
On Sun, 13 Feb 2005 19:08:26 -0500, ajb@spamcop.net
Quoting Josef Svenningsson
: I think it's unfair to the monad transformers to simply say that they don't obey the law. The interesting thing is whether they *preserve* the law. A monad transformer T preserves a law if given a monad M which obeys the law holds then the monad T M obeys the law.
The law in question is that mzero is a right-zero for bind. How can an underlying monad be said to "obey" this law if it doesn't support mzero?
You're of course absolutely right that it doesn't make sense to talk about mzero being a right-identity for bind if the monad doesn't support mzero. I should have been more clear. Let me have another try at explaining myself. Let's consider a specific monad transformer, say (ReaderT r). What I hope to convince you of is that (ReaderT r) cannot be said break the mzero-is-right-identity-for-bind law. Now, if we look at the MonadPlus instance for (ReaderT r) it looks like this: \begin{code} instance (MonadPlus m) => MonadPlus (ReaderT r m) where mzero = ReaderT $ \_ -> mzero m `mplus` n = ReaderT $ \r -> runReaderT m r `mplus` runReaderT n r \end{code} This important thing to note here is that the above instance declaration relies on an underlying monad m with mzero and mplus. If we try (and indeed succeed) to prove that (ReaderT r m) satisfies the mzero-is-right-identity-for-bind law we will see that the proof depend crucially on the fact that m also obeys the law. This is the best that the monad transformer can do, namely to preserve the law. You claimed that monad transformers break the mzero-is-right-identity-for-bind law because they can be applied to IO. I say, it's not the monad transformers fault. They cannot possibly be expected to repair the law if they are given a faulty monad. I hope this makes things a little clearer. /Josef