Dan Doel dan.doel at gmail.com
Fri Jul 10 18:16:59 EDT 2009

```On Friday 10 July 2009 4:35:15 am Wolfgang Jeltsch wrote:
> I fear that this instance doesn’t satisfy required laws. As far as I know,
> the following equalities should hold:
>
>     (*>) = (>>)
>
>     f *> empty = empty

IO already fails at this law, because (f *> empty) is not the same as empty,
it is a failing computation with the side effects of f. empty is only a left-

> This implies the following:
>
>     (f >> empty) <|> g = g
>
> But this wouldn’t hold with your instance. (f >> empty) <|> g would cause
> the side effects of f and of g, while g would (obviously) only cause the
> side effects of g.

Of course, this can be seen as a different symptom of the same underlying
problem (although if the initial equation for empty held, it'd work).

There's been talk before of splitting MonadPlus into multiple classes for
choice, which pick and choose which of these sorts of laws apply to each
but I can't recall if IO would satisfy all the laws for either.*

-- Dan

* For instance, you might expect MonadOrElse to satisfy:

f <|> g = f OR f <|> g = g

but IO will only satisfy:

f <|> g = f OR f <|> g = g-with-side-effects-from-f
```