Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Monad Transformers and lift function

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?

like image 670
Jcao02 Avatar asked Jun 20 '13 02:06

Jcao02


1 Answers

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.

like image 200
Daniel Gratzer Avatar answered Oct 10 '22 02:10

Daniel Gratzer