Monad 作为申请人的子类
从 GHC 7.10 开始,Applicative
是 Monad
的超类(即,每种类型的 Monad
也必须是 Applicative
)。Applicative
(pure
,<*>
)的所有方法都可以用 Monad
(return
,>>=
)的方法来实现。
很明显,pure
和 return
服务于同等目的,所以 pure = return
。<*>
的定义过于清晰:
mf <*> mx = do { f <- mf; x <- mx; return (f x) }
-- = mf >>= (\f -> mx >>= (\x -> return (f x)))
-- = [r | f <- mf, x <- mx, r <- return (f x)] -- with MonadComprehensions
-- = [f x | f <- mf, x <- mx]
此功能在标准库中定义为 ap
。
因此,如果你已经为类型定义了 Monad
的实例,那么你可以通过定义免费获得 Applicative
的实例
instance Applicative < type > where
pure = return
(<*>) = ap
与 monad 准则一样,这些等效性并未得到执行,但开发人员应确保始终坚持这些等效性。