Haskell MTL:如何退出monad并获取其中的值?

时间:2017-09-07 00:26:53

标签: haskell monads typeclass monad-transformers state-monad

我知道如何使用do块内每个monad的函数。但是一旦我完成了如何运行计算并获得结果?

run :: (MonadError Error m, MonadState State m) => m Int -> Int
run = ???

1 个答案:

答案 0 :(得分:5)

mtl的重点是你没有指定具体的monad变换器堆栈 - 你只需指定它必须处理错误并保持状态。

但是,一旦你真的想要运行这个动作,你需要把自己绑在一个特定的monad变换器堆栈上。该堆栈将告知您如何“运行”您的monadic动作。在您的情况下,您可能希望使用ExcepT Error (State State)

action :: (MonadError Error m, MonadState State m) => m Int
action = undefined

runAction :: State ->           -- initial state
             Either Error Int   -- account for possibility of error
runAction initialState = evalState (runExceptT action) initialState

请注意,此不是您可以做出的具体堆栈的唯一选择。事实上,你甚至可以交换StateExcept的顺序,并选择StateT State (Either Error)作为你的monad!

runAction :: State ->           -- initial state
             Either Error Int   -- account for possibility of error
runAction initialState = evalState action initialState

mtl对堆栈中monad的 order 一无所知这一事实是其缺点之一(也是有些人更喜欢坚持使用{{1}的原因之一}})。