什么是Haskell的Stream Fusion

时间:2009-02-23 15:42:01

标签: list optimization compiler-construction haskell

什么是Haskell的Stream Fusion以及如何使用它?

3 个答案:

答案 0 :(得分:62)

Logan指出的论文很棒,但有点困难。 (请问我的学生们。)这也是关于“流融合如何工作”以及“流融合是什么以及如何使用它”的一小部分。

流融合解决的问题是编写的功能代码经常分配中间列表,例如,创建一个无限的节点号列表,你可能会写

nodenames = map ("n"++) $ map show [1..]

朴素代码会分配一​​个无限的整数列表[1, 2, 3, ...],一个无限的字符串列表["1", "2", "3", ...],最终会有一个无限的名称列表["n1", "n2", "n3", ...]。分配太多了。

什么流融合会将像nodenames这样的定义转换为使用递归函数的东西,该递归函数仅分配结果所需的内容。通常,取消中间列表的分配称为砍伐森林

要使用流融合,您需要编写非递归列表函数,它们使用GHC ticket 915中描述的流融合库中的函数(map,{{ 1}}等等而不是显式递归。该库包含所有Prelude函数的新版本,这些函数已被重写以利用流融合。显然,这些东西将进入下一个GHC版本(6.12),但不是当前的稳定版本(6.10)。如果你想使用库Porges在他的回答中有一个很好的简单解释。

如果您真的想要解释流融合是如何工作的,请发布另一个问题---但这更难。

答案 1 :(得分:13)

据我所知,与Norman所说的相反,流融合是而不是目前在GHC的基础上实现(即你不能只使用Prelude函数)。有关详细信息,请参阅GHC ticket 915

要使用流融合,您需要安装流融合库,导入Data.List.Stream(您也可以导入Control.Monad.Stream)并仅使用该模块中的函数而不是Prelude函数。这意味着导入Prelude隐藏所有默认列表函数,而不是使用[x..y]构造或列表推导。

答案 2 :(得分:-2)

不正确,当6.12中的GHC默认使用这些新函数时,它们还会以非递归方式实现[x..y]和列表推导吗?因为它们不是正确行的唯一原因是它们是内部并且不是真正用Haskell编写的,而是更像关键字,为了速度和/或因为你无法重新定义那种语法。