Reputation: 321
I got the following error when implementing the Applicative instance for Cont
.
Couldn't match expected type ‘r’ with actual type ‘Cont r b’ ‘r’ is a rigid type variable bound by ...
newtype Cont r a = Cont {(>>-) :: (a -> r) -> r}
instance Functor (Cont r) where
-- fmap :: (a -> b) -> (Cont r) a -> (Cont r) b
fmap f (Cont cps_a) = Cont $ \cps -> cps_a (cps . f)
instance Applicative (Cont r) where
-- pure :: a -> Cont r a
pure x = Cont ($ x)
-- (<*>) Cont r (a -> b) -> Cont r a -> Cont r b
(Cont cps_f) <*> cont_cps_a = cps_f (\f -> fmap f cont_cps_a)
I am trying to use fmap
in defining (<*>)
, extracting f
from the left cps value then fmap f
over the right cps value. I am not sure where I made the mistake.
Upvotes: 2
Views: 258
Reputation: 2066
It is obvious that the type of expression cps_f (\f -> fmap f cont_cps_a)
is invalid . Since
fmap f cont_cps_a :: Cont r b
and
\f -> fmap f cont_cps_a :: (a->b)->Cont r b
and
cps_f :: ((a->b)->r)->r
cps_f
need parameter type as (a->b)->r
, but now is (a->b)->Cont r b
.
Instead of using fmap
, you still can implements <*>
operator similar to the way as your fmap
function as
(Cont cps_f) <*> Cont cps_a = Cont $ \cps_b -> cps_f (\f -> cps_a (cps_b . f))
Upvotes: 5