This is a general question, not tied to any one piece of code.
Say you have a type T a
that can be given an instance of Monad
. Since every mona
Functor
instances are typically very simple to define, I'd normally do those by hand.
For Applicative
and Monad
, it depends. pure
and return
are usually similarly easy, and it really doesn't matter in which class you put the expanded definition. For bind, it is sometimes benfitial to go the "category way", i.e. define a specialised join' :: (M (M x)) -> M x
first and then a>>=b = join' $ fmap b a
(which of course wouldn't work if you had defined fmap
in terms of >>=
). Then it's probably useful to just re-use (>>=)
for the Applicative
instance.
Other times, the Applicative
instance can be written quite easily or is more efficient than the generic Monad-derived implementation. In that case, you should definitely define <*>
separately.