<div dir="ltr"><div>Eight years later, I stumbled across this thread.</div><div><br></div><div>Here's a cute way to express commutativity of an applicative functor:</div><div><br></div><div>> forall f. flip (liftA2 f) == liftA2 (flip f)</div><div><br></div><div>Cuter yet,</div><div><br></div><div>> flip . liftA2 == liftA2 . flip</div><div><br></div><div>-- Conal</div></div><div class="gmail_extra"><br><div class="gmail_quote">On Wed, May 14, 2008 at 9:59 AM, David Menendez <span dir="ltr"><<a href="mailto:dave@zednenem.com" target="_blank">dave@zednenem.com</a>></span> wrote:<br><blockquote class="gmail_quote" style="margin:0 0 0 .8ex;border-left:1px #ccc solid;padding-left:1ex"><span class="">On Tue, May 13, 2008 at 9:06 PM, Ronald Guida <<a href="mailto:oddron@gmail.com">oddron@gmail.com</a>> wrote:<br>
> I have a few questions about commutative monads and applicative functors.<br>
><br>
>  >From what I have read about applicative functors, they are weaker than<br>
>  monads because with a monad, I can use the results of a computation to<br>
>  select between alternative future computations and their side effects,<br>
>  whereas with an applicative functor, I can only select between the<br>
>  results of computations, while the structure of those computations and<br>
>  their side effects are fixed in advance.<br>
><br>
>  But then there are commutative monads.  I'm not exactly sure what a<br>
>  commutative monad is, but my understanding is that in a commutative<br>
>  monad the order of side effects does not matter.<br>
><br>
>  This leads me to wonder, are commutative monads still stronger than<br>
>  applicative functors, or are they equivalent?<br>
><br>
>  And by the way, what exactly is a commutative monad?<br>
<br>
</span>A monad is commutative if the expression "a >>= \x -> b >>= \y -> f x<br>
y" is equivalent to "b >>= \y -> a >>= \x -> f x y". The identity,<br>
state reader, and maybe monads are commutative, for example.<br>
<br>
To put it another way, a monad is commutative if<br>
<br>
    liftM2 f a b = liftM2 (flip f) b a<br>
<br>
Since liftA2 generalizes liftM2, we can also say that an applicative<br>
functor is commutative if<br>
<br>
    liftA2 f a b = liftA2 (flip f) b a<br>
<br>
Or, put another way, if<br>
<br>
    a <*> b = flip ($) <$> b <*> a<br>
<br>
If w is a commutative monoid (that is, if mappend w1 w2 == mappend w2<br>
w1), then Const w is a commutative applicative functor.<br>
<br>
To summarize: some applicative functors are commutative, some<br>
applicative functors are monads, and the ones that are both are<br>
commutative monads.<br>
<span class="HOEnZb"><font color="#888888"><br>
--<br>
Dave Menendez <<a href="mailto:dave@zednenem.com">dave@zednenem.com</a>><br>
<<a href="http://www.eyrie.org/~zednenem/" rel="noreferrer" target="_blank">http://www.eyrie.org/~zednenem/</a>><br>
</font></span><div class="HOEnZb"><div class="h5">_______________________________________________<br>
Haskell-Cafe mailing list<br>
<a href="mailto:Haskell-Cafe@haskell.org">Haskell-Cafe@haskell.org</a><br>
<a href="http://www.haskell.org/mailman/listinfo/haskell-cafe" rel="noreferrer" target="_blank">http://www.haskell.org/mailman/listinfo/haskell-cafe</a><br>
</div></div></blockquote></div><br></div>