2012-07-04 63 views
4

我决定尝试并获得对管道的处理,并且我认为我做得很好,但是当我尝试使用导管4制作这个简单源代码时,我得到一个无限循环,不明白为什么。这是简化的,原始版本将创建一个临时文件名并通过yield返回。这只是返回一个()。无限循环源代码与导管

import Control.Monad.IO.Class 

import Data.Conduit 
import Data.Conduit.List as CL 

tempfiles :: MonadIO m => Source m() 
tempfiles = loop 
    where 
    loop = do 
     x <- liftIO $ print "tempfile" 
     yield x 
     loop 

如果我运行:

runResourceT $ (tempfiles $$ CL.take 5) 

我得到一个无限循环。为什么它不运行五次并给我一个五()s的列表?

+0

Minor nitpick:为什么'tempfiles = loop where loop = do ... loop'?为什么不只是'tempfiles =做... tempfiles'? –

+0

因为System.Posix.Temp中的mkstemp函数需要一个参数,所以tempfiles本身需要一个参数,但由于我正在递归并且该参数没有改变,而不是再次传递它,所以我只做了一个循环函数来完成递归与持续重用在顶层传入的参数。 –

+0

最终结果是这样的:https://gist.github.com/3051620老实说,这真是太酷了。本质上是一个无限的懒惰临时文件生成器。这个图书馆很有趣。 –

回答

4

在导管0.4中,收益不执行自动终止。这是0.5版本的一个重要变化;您的代码在那里按预期工作。

+0

嗯,我正在等待http-conduit,但我想这是一个很好的理由现在更新。谢谢。 –