Skip to content

Instantly share code, notes, and snippets.

@Daenyth
Last active May 11, 2023 15:12
Show Gist options
  • Save Daenyth/e5014ca0e1593f310fbd8d540b24a844 to your computer and use it in GitHub Desktop.
Save Daenyth/e5014ca0e1593f310fbd8d540b24a844 to your computer and use it in GitHub Desktop.
What's a monad

"Monad" is a word that describes a set of behaviors

In scala, we use the Monad[Foo] typeclass from cats to define instances of this behavior.

The essence of its behavior is the ability to describe a series of computations, where one computation depends on the result of the computation that came before it.

For example, Monad[Option] shows that the Option[A] data type can be used to describe computations of A which may result in no value.

case class Comment(text: String, author: Option[String])
case class User(name: String, email: String)
def getUser(name: String): Option[User] = ???

for {
  author <- comment.author
  user <- getUser(author)
} yield user.email

The above code shows an example of a dependent computation. Given a comment, we can maybe get the author. If we have the author, we can maybe look up a user. If we have the user, we can show their email.

We can write a method using the Monad interface to describe a computation which is valid for any data types that allow us to do sequential operations.

Monadic data structures allow us to abstract over control flow.

def oneThenAnother[F[_]: Monad, A, B, C](f1: A => F[B])(f2: B => F[C]): A => F[C] =
  (a: A) => f1(a).flatMap(b => f2(b))

The oneThenAnother method can be used on any data structure that allows monadic behavior.

When we use Monad[Option], we abstract over control flow where at any step can stop with no result

When we use Monad[Either[Throwable, *]], we abstract over control flow where any step can fail with a Throwable

When we use Monad[IO], we can abstract over computations that may be either synchronous or asynchronous and which are able to perform arbitrary actions during their execution.

Writing code using monads allows us to separate the concerns of control flow from the specific computations.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment