我知道Functor
和Applicative
应该是Monad
的超类,但不是出于历史原因。但是,为什么不能声明Monad
Functor
的实例?这将产生大致相同的效果,但无需修改现有代码。如果你想这样做,GHC抱怨:
instance Functor Monad where
fmap = liftM
Class `Monad' used as a type
In the instance declaration for `Functor Monad'
为什么?这可能是一个很好的理由。
答案 0 :(得分:11)
你的语法错了。 Monad
是类型类,而不是数据类型。你能写的是
instance Monad a => Functor a where fmap = liftM
但是,这只适用于扩展FlexibleInstances
(允许不属于T a1 a2 ... an
形式的实例,其中a1, a2, ... an
是类型变量且没有上下文)和{{1 (允许这个特定的实例[我不知道为什么需要这样])。
答案 1 :(得分:2)
原因是Monad
是一个类型类,而实例声明需要一个类型或类型构造函数。错误消息明确指出。类型类和类型是两种不同的东西。它们永远不会在Haskell中互换。