[Haskell-beginners] ListT + Writer

David McBride toad3k at gmail.com
Thu May 25 15:52:01 UTC 2017


ListT is a bit weird in that it affects whatever monad is underneath
it, so the order of your types in your Transformer stack matters.
Both ways have different meanings and each have legitimate uses.  In
any case you must use the lift function to get to the monad below the
one you are at.

import Control.Monad.List
import Control.Monad.Writer

test :: IO ()
test = do
  (runListT $ runWriterT  proc1) >>= print
  (runWriterT $ runListT proc2) >>= print
  return ()


proc1 :: Monad m => WriterT String (ListT m) Int
proc1 = do
  tell ("started: " :: String)
  x <- lift $ ListT (return [1,2])
  y <- lift $ ListT (return [3,4,5])
  lift $ guard (y /= 5)
  tell ("x:" ++ show x)
  tell ("y:" ++ show y)
  return (x * y)


proc2 :: Monad m => ListT (WriterT String m) Int
proc2 = do
  lift $ tell ("started: " :: String)
  x <- ListT (return [1,2])
  y <- ListT (return [3,4,5])
  guard (y /= 5)
  lift $ tell (" x:" ++ show x)
  lift $ tell (" y:" ++ show y)

  return (x * y)

On Thu, May 25, 2017 at 11:10 AM, Baa <aquagnu at gmail.com> wrote:
> Hello, everybody!
>
> I can process list in monad style with "do" syntax and to use "guard"
> function in the body. Something like:
>
>   fn :: [a] -> [a]
>   fn lst = do
>     el <- lst
>     guard $ condition el
>     ...
>     return $ change el
>
> How can I do the same but with possibility to call "tell" of "Write"
> monad in the fn's body? As I understand it should be:
>
>    ListT (Writer w) Int
>
> for this example?
>
> - but how to write it?
> - how to call (run) it?
> - and how is it safe ("transformers" package has bug in ListT, so "mtl"
>   must be used?)?
> - is there other canonical way to do it without to use fold*, recursive
>   calls/fix, State/RWS ?
>
>
> /Cheers
> _______________________________________________
> Beginners mailing list
> Beginners at haskell.org
> http://mail.haskell.org/cgi-bin/mailman/listinfo/beginners


More information about the Beginners mailing list