haskell - How to make this alternative definition of Maybe work? -
i hvae invended following alternative definition of maybe
:
type maybe' = forall b. (b -> (a -> b) -> b) :: -> maybe' = \d f -> f nothing :: maybe' nothing = const bind :: maybe' -> (a -> maybe' b) -> maybe' b bind ma f = ma nothing (\a -> f a)
the problem can't add following instance declaration
instance monad (maybe') return = >>= f = bind f
the error message :
type synonym maybe' should have 1 argument, has been given none
are there way fix?
you can make instance of monad
if wrap in newtype
. have use polymorphiccomponents
extension (a weaker form of rankntypes
) universally quantify b
:
{-# language polymorphiccomponents #-} newtype maybe' = maybe' { unmaybe' :: forall b. (b -> (a -> b) -> b) } :: -> maybe' = maybe' (\d f -> f a) nothing :: maybe' nothing = maybe' const bind :: maybe' -> (a -> maybe' b) -> maybe' b bind ma f = maybe' (unmaybe' ma const (\a -> unmaybe' (f a))) instance monad maybe' return = (>>=) = bind
the reason need newtype haskell type synonyms not "stick". when haskell tries match type signature of maybe'
without newtype against monad
type class, not see maybe'
@ , instead sees raw underlying function type.
haskell uses "principal types" ensure every type has normal form. normal form of underlying function is:
(->) b ((->) ((->) b) b)
type synonyms not change normal form of type, newtypes do. specifically, newtype
in case rearranging type normal form has a
last type parameter monad
instance requires.
Comments
Post a Comment