Personal tools

Monad Transformers

From HaskellWiki

(Difference between revisions)
Jump to: navigation, search
(Added links)
(update for mtl-2)
Line 1: Line 1:
There are currently two sets of packages that implement similar interfaces to [[Monad Transformers Explained|monad transformers]],
+
There are currently several packages that implement similar interfaces to [[Monad Transformers Explained|monad transformers]] (besides an additional package with a similar goal but different API named [[MonadLib]]):
besides a third package with a similar goal but different API named [[MonadLib]]:
 
   
* [http://hackage.haskell.org/package/mtl MTL] - Monad Transformers Library: provides concrete monad transformers like <hask>StateT</hask> and abstractions using [[multi-parameter type class]]es with [[functional dependencies]] like <hask>MonadState</hask>. Monads like <hask>State</hask> and their transformer counterparts like <hask>StateT</hask> are distinct types and can be accessed uniformly only through a type class abstraction like <hask>MonadState</hask>. Because of the functional dependencies, MTL can currently (2010-03) only used in [[Hugs]] and [[GHC]]. MTL was the first implementation.
+
* [http://hackage.haskell.org/package/transformers transformers]: provides the classes <hask>MonadTrans</hask> and <hask>MonadIO</hask>, as well as concrete monad transformers such as <hask>StateT</hask>. The monad <hask>State s a</hask> is only a type synonym for <hask>StateT s Identity a</hask>. Thus both <hask>State</hask> and <hask>StateT</hask> can be accessed by the same methods like <hask>put</hask> and <hask>get</hask>. However, this only works if <hask>StateT</hask> is the top-most transformer in a monad transformer stack. This package is Haskell 98 and thus can be also used with [[JHC]].
* The newer implementation is derived from the former one and is split into the following components:
+
* [http://hackage.haskell.org/package/mtl mtl] (Monad Transformer Library) comes in two versions:
** [http://hackage.haskell.org/package/transformers transformers]: Provide only concrete transformers like <hask>StateT</hask>. The monad <hask>State s a</hask> is only a type synonym for <hask>StateT s Identity a</hask>. Thus both <hask>State</hask> and <hask>StateT</hask> can be accessed by the same methods like <hask>put</hask> and <hask>get</hask>. However, this only works, if <hask>StateT</hask> is the top-most transformer in a monad transformer stack. This package is Haskell 98 and thus can be also used with [[JHC]].
+
** version 1 was the first implementation, containing the classes <hask>MonadTrans</hask> and <hask>MonadIO</hask>, concrete monad transformers such as <hask>StateT</hask> and [[multi-parameter type class]]es with [[functional dependencies]] such as <hask>MonadState</hask>. Monads like <hask>State</hask> and their transformer counterparts like <hask>StateT</hask> are distinct types and can be accessed uniformly only through a type class abstraction like <hask>MonadState</hask>. This version is now obsolete.
** [http://hackage.haskell.org/package/monads-fd monads-fd]: Provides the same type classes with functional dependencies like MTL. They allow using <hask>State</hask> methods also for <hask>StateT</hask> transformers within a transformer stack.
+
** version 2 re-exports the classes and monad transformers of the transformers package, and adds [[multi-parameter type class]]es with [[functional dependencies]] such as <hask>MonadState</hask>.
** [http://hackage.haskell.org/package/monads-tf monads-tf]: Provides a different abstraction using [[type families]]. Unfortunately the names of <code>monads-fd</code> and <code>monads-tf</code> clash, thus you can currently not import both packages in one package.
+
*:Version 2 of the MTL has some small [[Incompatibilities between MTL 1 and MTL 2|incompatibilities]] relative to version 1. See "[[Upgrading from MTL 1 to MTL 2]]" for instructions on how to make code written for version 1 work with version 2.
  +
:Because of the functional dependencies, MTL can currently (2010-03) only used in [[Hugs]] and [[GHC]]. MTL was the first implementation.
  +
* [http://hackage.haskell.org/package/monads-fd monads-fd]: this was the prototype of the new mtl implementation. It is now obsolete, and simply re-exports mtl.
  +
* [http://hackage.haskell.org/package/monads-tf monads-tf]: Provides a different abstraction using [[type families]]. Unfortunately the module names of <code>mtl</code> and <code>monads-tf</code> clash, so you can currently not import both packages in one package.
   
 
== How can I use MTL and transformers together? ==
 
== How can I use MTL and transformers together? ==
   
Q: When I use ghc or ghci it complains about the same module names in mtl and transformers or monads-fd. How can I resolve these name clashes?
+
MTL and transformers use different module names, but share common classes, type constructors and functions, so they are fully compatible.
A: You can use the <code>-hide-package</code> option of GHC. [[Cabal]] uses the <code>-hide-all-packages</code> option and then explicitly makes every package visible with <code>-package</code>.
 
   
 
== Shall I use MTL or transformers? ==
 
== Shall I use MTL or transformers? ==

Revision as of 13:34, 15 December 2010

There are currently several packages that implement similar interfaces to monad transformers (besides an additional package with a similar goal but different API named MonadLib):

  • transformers: provides the classes
    MonadTrans
    and
    MonadIO
    , as well as concrete monad transformers such as
    StateT
    . The monad
    State s a
    is only a type synonym for
    StateT s Identity a
    . Thus both
    State
    and
    StateT
    can be accessed by the same methods like
    put
    and
    get
    . However, this only works if
    StateT
    is the top-most transformer in a monad transformer stack. This package is Haskell 98 and thus can be also used with JHC.
  • mtl (Monad Transformer Library) comes in two versions:
    • version 1 was the first implementation, containing the classes
      MonadTrans
      and
      MonadIO
      , concrete monad transformers such as
      StateT
      and multi-parameter type classes with functional dependencies such as
      MonadState
      . Monads like
      State
      and their transformer counterparts like
      StateT
      are distinct types and can be accessed uniformly only through a type class abstraction like
      MonadState
      . This version is now obsolete.
    • version 2 re-exports the classes and monad transformers of the transformers package, and adds multi-parameter type classes with functional dependencies such as
      MonadState
      .
    Version 2 of the MTL has some small incompatibilities relative to version 1. See "Upgrading from MTL 1 to MTL 2" for instructions on how to make code written for version 1 work with version 2.
Because of the functional dependencies, MTL can currently (2010-03) only used in Hugs and GHC. MTL was the first implementation.
  • monads-fd: this was the prototype of the new mtl implementation. It is now obsolete, and simply re-exports mtl.
  • monads-tf: Provides a different abstraction using type families. Unfortunately the module names of mtl and monads-tf clash, so you can currently not import both packages in one package.

Contents

1 How can I use MTL and transformers together?

MTL and transformers use different module names, but share common classes, type constructors and functions, so they are fully compatible.

2 Shall I use MTL or transformers?

Transformers is Haskell 98 and thus more portable.

3 How to move from MTL to transformers?

Many package using MTL can be ported to transformers with only slight modifications. Modules require the Trans infix,

e.g.
import Control.Monad.State ...
must be replaced by
import Control.Monad.Trans.State ...
. Since
State
is only a type synonym, there is no longer a constructor named
State
. For constructing you must use the function
state
and instead of matching patterns you must call
runState
.

4 See also