Why isn't it necessary to use lift for executing a function in an internal monad transformer environment, except for IO? I mean, if I have StateT over WriterT and WriterT over ReaderT, why can I do this?

tell $ {- any code here for the Writer -}
foo <- asks {- This for the reader -}
and so on...

instead of

lift $ tell $ {- code ... -}
...

Is there an special explanation or it is only the way the Monad Transformers were written?

有帮助吗?

解决方案

It's because the Monad Transformer Library (MTL) recognizes that it's quite common for you to stack monads in just that way so they don't define tell as just some function (Mondoid w) => w -> Writer ().

Instead they have MonadWriter which is defined as a typeclass with tell as a function in it. Then they define a ton of instances of MonadWriter: ReaderT, IO, Writer (duh) etc. And thus you avoid the annoying repetition of lift..

This is quite common, any monad transformer (in MTL) will have a Control.Monad.***.Class which has this sort of typeclass.

许可以下: CC-BY-SA归因
不隶属于 StackOverflow
scroll top