An alternative approach: personally, I found that the way to learn Monads was the other way around. That is, after reading many tutorials and struggling to understand this subject for years, I:
- Learned Scala
- Learned the
- Learned how to use those in nested for-comprehensions (which are, on the surface, similar to nested for-loops in other languages)
- Learned how those for-comprehensions “desugar” (they are nothing but function calls into the data structures, and there’s a mechanical process for turning a for-comprehension into those function calls)
- Learned what those function calls actually do
- That’s basically it
There’s a lot of theory to Monads, and if you like that sort of thing, go for it. But in practice, Scala Monads are just types where there is a sensible definition for the
flatMap() methods. If you have those methods, it’s at least basically Monad-shaped.
(That is to say, in programming terms, Monads are effectively a design pattern, that happens to be so useful, so frequently, that Scala built first-class support for it into the language. The term comes from category theory, but you don’t have to know any category theory to understand them in practice.)
In principle, you also need some sort of
pure() method that constructs a new Monad instance out of a value – that tends to just be the basic constructor in standard Scala collections. Libraries like Cats make this more explicit than the language itself does.
So when I teach Monads at work, the above is how I usually go about it – for many people, it’s easiest to learn the theory by seeing it in practice first. It’s a bit over-simplified, and glosses over some of the theoretical details (there are some additional laws that a proper Monad is supposed to follow, which leads to frequent arguments about whether
Future is really a Monad), but that’s enough to be able to use Monads seriously and consistently in Scala.