
On Wed, Feb 16, 2011 at 11:28 PM, Sebastian Fischer
On Thu, Feb 17, 2011 at 11:32 AM, Evan Laforge
wrote: Or will there just be massive signature rewriting in the wake of mtl2?
I must admit I still don't understand your exact problem. Could you help me with an example where using mtl2 requires an additional (Functor m) constraint that is not required when using mtl1?
Sure. It could be I'm doing it wrong too, since I'm far from sure of myself here, and that's why I posted in the first place. Say you have a widely used monad: type CmdStack m = ThisT (ThatT m) newtype CmdT m a = CmdT (CmdStack m a) deriving (Everything) run_cmd_t (CmdT x) = x abort :: (Monad m) => CmdT m a abort = Error.throwError State.Abort f1 :: (Monad m) => CmdT m X f1 = fmap ... ... Follows are many modules full of functions that look like 'f1', or transitively call 'f1'. It used to be that (Monad m) implied (Functor m) but now evidently that is no longer so (the error is 'Could not deduce (Functor m) from the context (Monad m)'). The result is that every function that touches an fmap-using function needs a (Functor m) constraint. It goes for Applicative too, but evidently Applicative has Functor as a superclass, so adding just one is enough. It's even more fun because many functions may not require (Functor m)... but if you add an 'fmap' or <$> to something other functions call, I'm guessing there will be a ripple effect where you have to add Functor to every function that transitively calls it. So now when writing new functions you can choose between the wordy safe way or the concise way which might work now but break later. I don't really understand what benefit I get from the change, but hopefully it's significant because the signatures do get significantly uglier and it affects every single one. And since there's no way to abstract over class contexts aside from declaring a dummy class, there's no way that I know of to insulate from changes like this.