foldr与foldl(或foldl')的含义

首先,我正在阅读的真实世界Haskell说永远不会使用foldl ,而是使用foldl' 。 所以我相信它。

但是我对什么时候使用foldr vs. foldl'很朦胧。 虽然我可以看到他们在我面前的工作方式不同,但我太愚蠢地无法理解何时“哪个更好”。 我想在我看来,它应该无关紧要,因为它们都产生相同的答案(不是吗?)。 事实上,我之前使用这个构造的经验来自Ruby的inject和Clojure的reduce ,它们似乎没有“左”和“右”版本。 (侧面问题:他们使用哪个版本?)

任何能够帮助像我这样智能挑战的洞察力都将受到高度赞赏!


foldr fx ys的递归,其中ys = [y1,y2,...,yk]看起来像

f y1 (f y2 (... (f yk x) ...))

foldl fx ys的递归看起来像

f (... (f (f x y1) y2) ...) yk

这里的一个重要区别是,如果fxy的结果只能使用x的值计算,那么foldr不需要检查整个列表。 例如

foldr (&&) False (repeat False)

返回False

foldl (&&) False (repeat False)

永不终止。 (注意: repeat False会创建一个无限列表,其中每个元素都是False 。)

另一方面, foldl'是尾递归和严格的。 如果你知道你不得不遍历整个列表(例如,将列表中的数字相加),那么foldl'foldr更具有空间效率(可能更具时间效率)。


foldr看起来像这样:

foldl看起来像这样:

上下文:在Haskell wiki上折叠


它们的语义不同,所以你不能只交换foldlfoldr 。 一个从左边折叠元素,另一个从右边折叠。 这样,运营商就可以按照不同的顺序申请。 这对所有非关联操作都很重要,例如减法。

Haskell.org有关这个主题的一篇有趣的文章。

链接地址: http://www.djcxy.com/p/80721.html

上一篇: Implications of foldr vs. foldl (or foldl')

下一篇: Haskell function composition