In the following instance of Monad:
instance Monad ((->) r) where return = const f >>= k = \ r -> k (f r) r Is this forcing k to be a function of two parameters? And if so, why would you want to pass (f r) AND r to k?
Is this forcing k to be a function of two parameters?
Yes. Looking at the definition of Monad, we have
class Monad m where return :: a -> m a (>>=) :: m a -> (a -> m b) -> m b Substituting (->) r for m, we have
return :: a -> (->) r a (>>=) :: (->) r a -> (a -> (->) r b) -> (->) r b Now, (->) r a is just a weird syntax for r -> a, and similarly for the other cases, so we get
return :: a -> r -> a (>>=) :: (r -> a) -> (a -> r -> b) -> r -> b So we can see that indeed the second argument to >>= must be a function of (at least) two arguments.
Why? Because a function of two arguments is just a function taking one argument and returning a function of one argument, while the second argument to >>= should be a function taking one argument and returning a value of the monad's type constructor; for the function monad, this value will be a function. Hence the second argument to >>= will be a function of two arguments.
[W]hy would you want to pass (f r) AND r to k?
Partly because it makes the (->) r type fit the uniform structure of a Monad, which is useful for lots of reasons.
Partly k doesn't know which function f you're using. That means that, from k's perspective, the two arguments f r and r really are independent --- k can't calculate one from the other.
Consider this function:
-- | 'f' takes two numbers and adds them together f :: (->) (Int, Int) Int f = fst >>= \ n0 -> snd >>= \ n1 -> return (n0 + n1) The function \ n0 -> snd >>= \ n1 -> return (n0 + n1) doesn't care where its argument comes from, or in particular that its argument is the first component of the input. So it needs both the argument n0 and the full input.
kis a functiona -> r -> b.ris the only instance ofryou have andf ris the only way to get anaso you don't have much choice.