# A Scala Comonad Tutorial, Part 1

In chapter 11 of our book, we talk about monads in Scala. This finally names a pattern that the reader has seen throughout the book and gives it a formal structure. We also give some intuition for what it means for something to be a monad. Once you have this concept, you start recognizing it everywhere in the daily business of programming.

Today I want to talk about comonads, which are the dual of monads. The utility of comonads in everyday life is not quite as immediately obvious as that of monads, but they definitely come in handy sometimes. Particularly in applications like image processing and scientific computation.

Let’s remind ourselves of what a monad is. A monad is a functor, which just means it has a `map` method:

This has to satisfy the law that `map(x)(a => a) == x`, i.e. that mapping the identity function over our functor is a no-op.

A monad is a functor `M` equipped with two additional polymorphic functions; One from `A` to `M[A]` and one from `M[M[A]]` to `M[A]`.

Recall that `join` has to satisfy associativity, and `unit` has to be an identity for `join`.

In Scala a monad is often stated in terms of `flatMap`, which is `map` followed by `join`. But I find this formulation easier to explain.

Every monad has the above operations, the so-called proper morphisms of a monad, and may also bring to the table some nonproper morphisms which give the specific monad some additional capabilities.

For example, the `Reader` monad brings the ability to ask for a value:

The meaning of `join` in the reader monad is to pass the same context of type `R` to both the outer scope and the inner scope:

The `Writer` monad has the ability to write a value on the side:

The meaning of `join` in the writer monad is to concatenate the “log” of written values using the monoid for `W` (this is using the `Monoid` class from Scalaz):

And the meaning of `unit` is to write the “empty” log:

The `State` monad can both get and set the state:

The meaning of `join` in the state monad is to give the outer action an opportunity to get and put the state, then do the same for the inner action, making sure any subsequent actions see the changes made by previous ones.

The `Option` monad can terminate without an answer:

Note that counit is pronounced “co-unit”, not “cow-knit”. It’s also sometimes called `extract` because it allows you to get a value of type `A` out of a `W[A]`. While with monads you can generally only put values in and not get them out, with comonads you can generally only get them out and not put them in.

And instead of being able to `join` two levels of a monad into one, we can `duplicate` one level of a comonad into two.

Kind of weird, right? This also has to obey some laws. We’ll get to those later on, but let’s first look at some actual comonads.

A simple and obvious comonad is the dumb wrapper (the identity comonad):

This one is also the identity monad. `Id` doesn’t have any functionality other than the proper morphisms of the (co)monad and is therefore not terribly interesting. We can get the value out with our `counit`, and we can vacuously `duplicate` by decorating our existing `Id` with another layer.

It should be obvious how we can give a `Comonad` instance for this (I’m using the Kind Projector compiler plugin to make the syntax look a little nicer than Vanilla Scala):

Arguably, this is much more straightforward in Scala than the reader monad. In the reader monad, the `ask` function is the identity function. That’s saying “once the `R` value is available, return it to me”, making it available to subsequent `map` and `flatMap` operations. But in `Coreader`, we don’t have to pretend to have an `R` value. It’s just right there and we can look at it.

So `Coreader` just wraps up some value of type `A` together with some additional context of type `R`. Why is it important that this is a comonad? What is the meaning of `duplicate` here?

To see the meaning of `duplicate`, notice that it puts the whole `Coreader` in the value slot (in the `extract` portion). So any subsequent `extract` or `map` operation will be able to observe both the value of type `A` and the context of type `R`. We can think of this as passing the context along to those subsequent operations, which is analogous to what the reader monad does.

In fact, just like `map` followed by `join` is usually expressed as `flatMap`, by the same token `duplicate` followed by `map` is usually expressed as a single operation, `extend`:

Notice that the type signature of `extend` looks like `flatMap` with the direction of `f` reversed. And just like we can chain operations in a monad using `flatMap`, we can chain operations in a comonad using `extend`. In `Coreader`, `extend` is making sure that `f` can use the context of type `R` to produce its `B`.

Chaining operations this way using `flatMap` in a monad is sometimes called Kleisli composition, and chaining operations using `extend` in a comonad is called coKleisli composition (or just Kleisli composition in a comonad).

The name `extend` refers to the fact that it takes a “local” computation that operates on some structure and “extends” that to a “global” computation that operates on all substructures of the larger structure.

Just like the writer monad, the writer comonad can append to a log or running tally using a monoid. But instead of keeping the log always available to be appended to, it uses the same trick as the reader monad by building up an operation that gets executed once a log becomes available:

Note that `duplicate` returns a whole `Cowriter` from its constructed `run` function, so the meaning is that subsequent operations (composed via `map` or `extend`) have access to exactly one `tell` function, which appends to the existing log or tally. For example, `foo.extend(_.tell("hi"))` will append `"hi"` to the log of `foo`.

1. Left identity: `wa.duplicate.extract == wa`
2. Right identity: `wa.extend(extract) == wa`
3. Associativity: `wa.duplicate.duplicate == wa.extend(duplicate)`

It can be hard to get an intuition for what these laws mean, but in short they mean that (co)Kleisli composition in a comonad should be associative and that `extract` (a.k.a. `counit`) should be an identity for it.

Very informally, both the monad and comonad laws mean that we should be able to compose our programs top-down or bottom-up, or any combination thereof, and have that mean the same thing regardless.

## Next time…

In part 2 we’ll look at some more examples of comonads and follow some of the deeper connections. Like what’s the relationship between the reader monad and the reader comonad, or the writer monad and the writer comonad? They’re not identical, but they seem to do all the same things. Are they equivalent? Isomorphic? Something else?