As opposed to the internal logic of monads, how they work, I hope to start a discussion about their external logic: how and why to use monads.
design
------
How do monads change the way one
* thinks about a problem?
* structures data?
* refactors?
* tests?
Should I always be giving the monads a lot of cognitive bandwidth, because they reorder the way everything should be, or is it an investment with a high initial cognitive cost but requiring little maintenance thereafter?
what is their common framework?
-------------------------------
Monads let data reach farther than it otherwise would. Subjectively, they feel like a controlled way of violating encapsulation.
Are there other, deeper or more specific, commonalities that explain why monads are a good way to implement exceptions, output, state, and perhaps other services?
varieties
---------
In practice, are all monads either for exceptions, state or output? If not, what other goals are monads well suited to?
How should multiple contexts coexist? What's a simple Haskell program that uses more than one kind of monad in the same scope? Should, say, output and state be nestled in parallel into a three-attribute monad (the third variable being the type variable), or would it instead be better to create separate output and state monads? If each context should have a separate monad, is it a good idea to nest them, or somehow otherwise let them overlap, within a particular function or scope?
temptations to err
------------------
I have a vague sense that a common pitfall is to use monads to do things in a procedural way that eliminates the benefits of a functional language, but I'm not sure I would recognize it if I were making that error. I feel like I could learn from a comparison of code that works and uses monads badly to code that does better.