4 ms·
Heres what finally got me to understand monads, including some of the context around them: 1. Why is it important that a List is a monad? A. Its not particula
by bonobo3000 11y ago
Heres what finally got me to understand monads, including some of the context around them:
1. Why is it important that a List is a monad?
A. Its not particularly important. Its really just pointing out that monad is a very general abstraction - it wont tell you anything you don't already know about Lists.
On the other side, lists as kind of trivial examples of monads - they didnt really help me understand monads either.
Its like saying 1 is a real number - true, but it wont help you understand real numbers.
2. Why should i use monads?
A: I like to think of monads as things you can use in a for-comprehension (or the do notation in Haskell). If you can imagine writing something like
for {x <- thing; y<-thing} x + y
for "thing", then "thing" might be a monad (assuming all the math laws work out - sometimes they don't). In scala, for-comprehensions are literally de-sugared into maps/flatMaps/filters so for comprehension without filter <=> monad.
3. But a monad is just a monoid in the category of endofunctors?
A: There is deep category theory and math behind this stuff. It can be useful to talk about it, but when you are starting out its overkill. Don't worry about "getting" the really abstract crap at first, just skim right over. Programming in monads is a lot easier than the theory, and the theory can be learned after getting your hands dirty. Using monads is mostly just for-comprehensions.
ps:
"monoid" = there is a zero, and an add operation. like integers with +, or integers with *).
"functor" = thing that has a map() operation.
"endo" = self
"category" = kind of like a set. its a container.
So a monad has a "zero" or default monad, a way to add monads, and a map operation that returns another monad.
e.g List -> zero = Nil, add = append, map = the "normal" map with f applied to each element
Future -> zero = empty Future, add = do future2 after future1, map = make a future with the f applied to value
- meowface 11y agoWhat helped me grok monads was to understand that monads are just a subset of functors. Then I did what I could to fully understand what functors were, since at that point they were still a kind of cargo-cult black box for me. let liftF = fmap liftF negate (Just 1) liftA negate (Just 1) liftM negate (Just 1) Realizing these all performed the same operation (if operating on a monadic value), and that `fmap` is just a `liftF` ("lift a regular function to work on a functor"), cleared some things up for me. This also helped: https://en.wikibooks.org/wiki/Haskell/Applicative_functors#A_sliding_scale_of_power https://en.wikibooks.org/wiki/Haskell/Applicative_functors#A... So all these abstractions really just let you do different things with functions that normally don't take functor arguments. They make the function basically allow functor arguments (kind of), to save writing a lot of boilerplate within your functions; typically boilerplate that would be put at the start of every function. Once someone really gets the idea of what a functor is and why they can be useful, I think the rest is easy to understand once you read the definition of monads and applicatives.