# Monad Transformers

### From HaskellWiki

(Changed link to "All About Monads") |
(turning all <hask> tags into <code> tags... I dont know how to fix the BUG of <hask> tag where there's NO SPACE after it, totally unreadable!) |
||

(2 intermediate revisions by one user not shown) | |||

Line 1: | Line 1: | ||

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]]): |
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]]): |
||

− | * [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]]. |
+ | * [http://hackage.haskell.org/package/transformers transformers]: provides the classes <code>MonadTrans</code> and <code>MonadIO</code>, as well as concrete monad transformers such as <code>StateT</code>. The monad <code>State s a</code> is only a type synonym for <code>StateT s Identity a</code>. Thus both <code>State</code> and <code>StateT</code> can be accessed by the same methods like <code>put</code> and <code>get</code>. However, this only works if <code>StateT</code> is the top-most transformer in a monad transformer stack. This package is Haskell 98 and thus can be also used with [[JHC]]. |

* [http://hackage.haskell.org/package/mtl mtl] (Monad Transformer Library) comes in two versions: |
* [http://hackage.haskell.org/package/mtl mtl] (Monad Transformer Library) comes in two versions: |
||

− | ** 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. |
+ | ** version 1 was the first implementation, containing the classes <code>MonadTrans</code> and <code>MonadIO</code>, concrete monad transformers such as <code>StateT</code> and [[multi-parameter type class]]es with [[functional dependencies]] such as <code>MonadState</code>. Monads like <code>State</code> and their transformer counterparts like <code>StateT</code> are distinct types and can be accessed uniformly only through a type class abstraction like <code>MonadState</code>. This version is now obsolete. |

− | ** 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>. |
+ | ** 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 <code>MonadState</code>. |

*: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. |
*: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. |
: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-fd monads-fd]: this was the prototype of the new mtl implementation. It is now obsolete, and simply re-exports mtl version 2. |

* [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. |
* [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. |
||

Line 16: | Line 16: | ||

== Shall I use MTL or transformers? == |
== Shall I use MTL or transformers? == |
||

− | Transformers is Haskell 98 and thus more portable. |
+ | Transformers is Haskell 98 and thus more portable, and doesn't tie you to functional dependencies. |

+ | But because it lacks the monad classes, you'll have to lift operations to the composite monad yourself ([http://hackage.haskell.org/packages/archive/transformers/latest/doc/html/Control-Monad-Trans-Class.html#g:2 examples]). |
||

== How to move from MTL to transformers? == |
== How to move from MTL to transformers? == |
||

Line 22: | Line 22: | ||

Many package using <code>MTL</code> can be ported to <code>transformers</code> with only slight modifications. |
Many package using <code>MTL</code> can be ported to <code>transformers</code> with only slight modifications. |
||

Modules require the <code>Trans</code> infix, |
Modules require the <code>Trans</code> infix, |
||

− | e.g. <hask>import Control.Monad.State ...</hask> must be replaced by <hask>import Control.Monad.Trans.State ...</hask>. |
+ | e.g. <code>import Control.Monad.State ...</code> must be replaced by <code>import Control.Monad.Trans.State ...</code>. |

− | Since <hask>State</hask> is only a type synonym, there is no longer a constructor named <hask>State</hask>. |
+ | Since <code>State</code> is only a type synonym, there is no longer a constructor named <code>State</code>. |

− | For constructing you must use the function <hask>state</hask> and instead of matching patterns you must call <hask>runState</hask>. |
+ | For constructing you must use the function <code>state</code> and instead of matching patterns you must call <code>runState</code>. |

== See also == |
== See also == |

## Latest revision as of 11:59, 6 July 2011

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.

- version 1 was the first implementation, containing the classes

- 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 version 2.
- 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 |

## [edit] 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.

## [edit] 2 Shall I use MTL or transformers?

Transformers is Haskell 98 and thus more portable, and doesn't tie you to functional dependencies. But because it lacks the monad classes, you'll have to lift operations to the composite monad yourself (examples).

## [edit] 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`

.

## [edit] 4 See also

- Monad Transformers Explained
- Monad Transformers Step by Step (PDF)
- All About Monads
- http://www.haskell.org/pipermail/libraries/2009-March/011415.html
- http://www.haskell.org/pipermail/libraries/2009-December/012914.html
- http://www.haskell.org/pipermail/haskell-cafe/2010-January/071842.html
- http://www.mail-archive.com/debian-haskell@lists.debian.org/msg01241.html