[英]Pipes `run` with State
我有一个制片人:
p:: Producer Message IO r
。
我可以使用以下方法处理所有消息:
runEffect $ for p processMessage
在哪里
processMessage:: Message -> Effect IO ()
。
如何使用以下方法实现有状态处理:
processMessage:: Message -> Effect (StateT MyState IO) ()
?
简短的回答:
processMessage
很好runEffect
返回StateT MyState IO ()
,你需要评估它用一个虚拟例子来回答更长的问题:
您的生产者被锁定在IO
monad 中,您需要将其修改为在MonadIO m
或显式 state monad 中。
import Control.Monad.State
import Pipes
type Message = Int
p :: MonadIO m => Producer Message m ()
p = each [1..10]
您的processMessage
的签名已经很好了。 我正在遵循您的签名并添加一些简单的逻辑来练习 IO 和 State 功能
processMessage :: Message -> Effect (StateT MyState IO) ()
processMessage msg = do
modify (+ msg)
liftIO (print msg)
然后是最后一步。 runEffect:: Monad m => Effect m r -> m r
, if you substitute the m
with a concrete type, this ends up being runEffect:: Effect (StateT MyState IO) () -> StateT MyState IO ()
, meaning that您将剩下 state monad 仍然需要执行。 执行 state monad、 runStateT
、 evalStateT
和execStateT
有三种变体。 在本例中,我选择了execStateT:: StateT MyState IO () -> IO MyState
变体,但在您的情况下选择您需要的任何一个。
main :: IO ()
main = do
st <- execStateT (runEffect $ for p processMessage) 0
putStrLn $ "End state: " <> show st
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.