# What is a monad

*Monad* is a trait with the following operations:

` `

Having such trait implementation for a type `M`

makes it a monad *instance*.

Sometimes, `pure`

is called `return`

or `point`

, whereas `bind`

might instead be named `flatMap`

(preferred in Scala) or `>>=`

(Haskell's way). The method names are not so important, what's important is their signatures and what they do.

`pure`

and `bind`

implementations must obey some easily google-able mathematical laws omitted here to make things less boring.

`M`

type parameter

Type parameter of higher kind `M`

requires a monad instance to be parameterized by a type with a single type parameter, e.g. `List`

, `Future`

, `Option`

, `({ type λ[A] = Either[Throwable, A] })#λ`

, or any type similar to:

` `

`pure`

operation

In a nutshell, `pure`

gives a way to wrap a value of type `A`

into type `M`

(sometimes called *monadic context*). E.g.: `List(a)`

, `Future { a }`

, `Some(a)`

, `Right[Throwable, A](a)`

. Put clearly: `pure`

is `A => M[A]`

, and that's it.

`bind`

operation

The essence of this operation is to allow *flattening* of `M[M[A]]`

to `M[A]`

. This might be not clear immediately, given the above `Monad`

trait definition, but that's easy to understand: having a value `ma: M[A]`

and a function `f: A => M[B]`

, to apply this function to `ma`

, one needs a way to apply `f`

to an `a: A`

that's inside the context M, and the result will be of type `M[M[B]]`

. So, `bind`

allows to apply a function to monadic values and to flatten nested monadic contexts, while `pure`

- to add new ones. For example, `List(a).flatMap(a => List(a))`

, `Future { a } flatMap { a => Future { a } }`

, `Some(a).flatMap(a => Some(a))`

. These are artificial examples, but it's easy to imagine some nested conditional logic in the supplied `f`

function.

## Different perspective on `Monad`

trait

It turns out, `Monad`

trait might be formulated in a different way that is closer to the flattening intuition above:

` `

Here, `join`

(or `flatten`

) does exactly that. Also, we've got a `map`

operation which is needed to fill the 'gap' from loosing the full power of `bind`

. Those two definitions are equivalent: `bind`

can be implemented in terms of `join`

and `map`

:

` `

or `map`

and `join`

in terms of `bind`

and `pure`

:

` `

## Different perspective on `map`

and `bind`

There is also an alternative view on `map`

and `bind`

methods signatures. Let's call 'em `lift`

and `liftM`

accordingly:

` `

Notice how similar they are. Both take a function, either ordinary `A => B`

in case of `lift`

or a monadic one `A => M[B]`

(sometimes called *Kleisli arrow*) in case of `liftM`

, and *lift* it to a function that works on monadic values. And these definitions are easily expressible in terms of original `map`

/`bind`

:

` `

So, from this perspective, a monad can also be defined using `pure`

and `liftM`

or `pure`

, `join`

, and `lift`

.

## The essence of monads

From the dry definition above it might be not clear how monads can be useful, why they exist in the first place. So, to put it simply, monads give a way to chain computations (of type `A => M[B]`

) while abstracting some details of how to exactly do that (extract values out of monadic context and flatten nested contexts) into the monad itself. For example, for `Lists`

s it performs flattening, for `Option`

s it stops on first `None`

, for `Future`

s - allows to make another asynchronous computation from within asynchronous computation, for some more esoteric *state* monad - to emulate mutable state in pure functional setting. This is what actually happens in Scala when using *for comprehension* syntax (though it doesn't force to implement any kind of trait, like the `Monad`

above: just follow the method signatures, and all' be fine):

` `

And it's just a syntax sugar for:

` `

Unlike the `Monad`

trait definition above, monadic operations here are written in object-oriented style, but that doesn't change their meaning.

## Some monad instances

A monad's essence is in how chaining (`bind`

operation) is implemented. So, here some monads instances to make it all clearer:

` `

Notice how partial type application is used for `Either`

which has two type parameters while monad requires just one. In general, for types having more than one type parameter, one needs to *fix* all the parameters but one to make an, in fact, a new type that could potentially be a monad instance.

# Conclusion

Don't expect to understand the nature of monads just in one seat if you are new to them: you definitely need to play with various monads, see how they behave, implement some of them on your own. But the underlying idea is simple and is just a common programming practice: separate concerns and, as a consequence, prevent code duplication, by moving common stuff into a single easily maintainable and comprehensible place.