Function composition hint
function-composition, haskell, monads, reader-monad, type-inference
Solution
The explanation is:
- Your `return` is (perhaps unexpectedly) of a different monad than your `=<<`.
- The monad it uses is the reader monad `(->) r`.
The compiler tries to unify the result of `return :: c -> m' c` with the first argument of `(a -> m b) -> m a -> m b`, so to unify `m' c` with `a -> m b`. The only possibility is that `m'` is the reader monad `(->) r` for some `r`. Next, it tries to unify `(->) r c` with (converted to the prefix notation) `(->) a (m b)`, which is solved by setting `r` to `a` and `c` to `m b`. So, after unification, the compiler gets the most general possible type
return :: (m b) -> ((->) a (m b))
or in the usual infix notation
return :: (m b) -> (a -> m b)
See also:
- How to use (->) instances of Monad and confusion about (->)
- The source where the instance of `Monad ((->) r)` is defined.
Edit: To define a monad, we need a (partially applied) type of kind `* -> *`. These are almost always partially applied data constructors, but this particular case, we view `->` as a type operator that takes 2 type arguments and creates a new type (the function type). So for any given type `r`, the partially applied expression `(->) r` is a type of kind `* -> *`. As it turns out, there is a straightforward way how to describe monad operations on it. See Control.Reader monad and also this article that explains it. The monad operations for `Reader` are implemented exactly the same way as for `(->)`, the only difference is that `Reader` wraps the operations into a distinct data type.
Problem
just looking for an explanation how does following composition work: ``` (=<<) . return ``` where ``` (=<<) :: (a -> m b) -> m a -> m b return :: a -> m a (.) :: (b -> c) -> (a -> b) -> a -> c ``` The final type: ``` GHCi> :t (=<<) . return (=<<) . return :: Monad m => m b -> m a -> m b ``` I cann't grasp how can match m a with (a -> m b) , ie. how can apply result of return which is a simple type to first argument of (=<<) expecting a function type ?