我正在探索使用Conduit包以在Haskell中实现复杂事件处理的可能性。举例来说,我想使用Conduit实现累加功能。

从...开始:

#!/usr/bin/env stack
-- stack script --resolver lts-8.12 --package conduit-combinators
{-# LANGUAGE ExtendedDefaultRules #-}
import Conduit

trans :: Monad m => ConduitM Int Int m ()
trans = do
    mapC (* 2)

main :: IO ()
main = runConduit $ yieldMany [1..10] .| trans .| mapM_C print


我得到:


2 4 6 8 10 12 14 16 18 20


我如何修改trans以便产生


1 3 6 10 15 21 28 36 45 55


代替?

最佳答案

scanlC,它是“列表的scanl的模拟”,几乎可以满足您的要求。我说“几乎”是因为scanlC会要求并产生一个初始的“种子”值,您不需要也不需要(参见scanlscanl1之间的差异)。这样,您将需要显式提供第一个流值作为种子:

trans :: Monad m => ConduitM Int Int m ()
trans = await >>= maybe (return ()) (scanlC (+))


(显然,劣等选择是在管道的下一步中使用trans = scanlC (+) 0并使用dropC 1来摆脱0。)

关于haskell - 使用管道实现累加功能,我们在Stack Overflow上找到一个类似的问题:https://stackoverflow.com/questions/49235610/

10-13 04:38