库函数用n次组成一个函数

kes*_*kes 37 haskell

Haskell中是否有一个库函数可以自己编写一个函数n次?

例如,我有这个功能:

func :: a -> a
Run Code Online (Sandbox Code Playgroud)

我想这样做:

func . func . func . func . func . func , ... 
Run Code Online (Sandbox Code Playgroud)

(最多n次,其中n仅在运行时已知).

请注意,迭代函数不适合我正在做的事情,因为我不关心任何中间结果.

Rei*_*ton 54

iterate解决方案是好的,否则你可能会喜欢这一个:的组成n的副本ffoldr (.) id (replicate n f).

  • @John其他解决方案(带有`!!`或`lookup.zip`的`iterate`)也适用于n == 0.查看[iterate的定义](http://haskell.org/ghc/docs/ 6.12.1/html/libraries/base-4.2.0.0/src/GHC-List.html#iterate)你会看到它以基本情况开始列表. (6认同)
  • 我喜欢这个,因为它也适用于n == 0. (2认同)

Tho*_*son 24

\xs n -> iterate func xs !! n
Run Code Online (Sandbox Code Playgroud)

我不知道为什么,但我觉得xs在学习Haskell时人们并没有经常接触到这些东西.

如果您不喜欢,n那么您可以使用funciterate作为替代方案.(某些人/群组/工具不喜欢在某些情况下调用"错误"的函数,我并不认为在这些情况下查找更好)

lookup n . zip [0..] . iterate func
Run Code Online (Sandbox Code Playgroud)

编辑:好的,所以我删除,则未删除,因为我与其他回答者同意-你不应该使用折扣迭代的,只是因为它给你更多的比你的需要.

  • 是的,在我看来,这是一个当之无愧的耻辱,但它真正意味着你必须小心在可能不适用的情况下使用它 - 而不是你永远不应该使用它.正如trinithis指出的那样,在这种情况下,除非传递负指数,否则它不会出错.顺便说一句!! 实际上是一个明显比查找更好的选择:查找和zip将永远循环在负索引上,寻找不存在的结果,但!! 将立即失败,因为它知道指数不能为负. (9认同)
  • 因为它的价值,因为`iterate`保证了一个无限的列表,我会使用``(`)`或`genericIndex`来使用`zip`和`zip`. (2认同)

Tsu*_*Ito 12

我不知道你为什么说iterate不合适.它非常适合这个目的. (!! n) . iterate funcn复制品的组成func.

(有人发布了类似上面代码的答案,但他/她似乎已将其删除了.)


Tho*_*ing 12

(\n -> appEndo . mconcat . replicate n . Endo) n f x


Aky*_*Aky 8

我是Haskell的初学者,目前在第5章("高阶函数")中学习你是一个很好的Haskell!所以我还不熟悉之前回复中显示的功能.根据我到目前为止的理解,我会这样做:

applyNTimes :: Int -> (a -> a) -> a -> a
applyNTimes n f x 
    | n == 0        = x
    | otherwise     = f (applyNTimes (n-1) f x)
Run Code Online (Sandbox Code Playgroud)

  • 请注意,这比`|严格要好 否则= applyNTimes(n-1)f(fx)`,因为`f`可能是懒惰的. (6认同)
  • 我唯一不同的是模式匹配而不是使用保护:`applyNTimes 0 _ x = x`然后`applyNTimes nfx = f $ applyNTimes(n-1)fx`.实际上,你应该能够从中删除所有的x. (4认同)

Cha*_*er5 5

这是一个复杂度为 O(log n) 而不是 O(n) 的版本(构建函数,而不是应用它):

composeN 0 f = id
composeN n f
    | even n = g
    | odd  n = f . g
    where g = g' . g'
          g' = composeN (n `div` 2) f
Run Code Online (Sandbox Code Playgroud)

  • @matt可能是因为我参加聚会迟到了,并且因为当您仍然需要 O(N) 时间来执行它时,构建该函数的时间复杂度并不真正相关。 (2认同)