Haskell的pure
功能与return
相同吗?
如果Monad已经是Applicative的一个实例,我可以创建一个Monad实例,对吧?所以我想知道Applicative的pure
是否每次都可以与Monad的return
互换?有没有一个例子,他们不一样?
data HelloType a = HelloType { getValue :: a } deriving (Show, Eq)
instance Functor HelloType where
fmap f (HelloType y) = HelloType (f y)
instance Applicative HelloType where
(<*>) (HelloType f) (HelloType x) = HelloType (f x)
pure = HelloType
instance Monad HelloType where
(>>=) (HelloType x) f = f x
-- return = pure
return = HelloType
plus3 :: (Num a) => Maybe a -> HelloType (Maybe a)
plus3 (Just x) = HelloType (Just $ x + 3)
plus3 Nothing = HelloType Nothing
main= do
let withPure = pure (Just 3) >>= plus3 >>= plus3
withReturn = return (Just 3) >>= plus3 >>= plus3
print $ withPure == withReturn -- TRUE
作为Monad实例的每一种类型必须使其return
等于pure
。
特别是,由于Applicative
是Monad
的超类,return
不需要定义,因为默认情况下它被定义为pure
的同义词:请参阅the definition:
此外,Monad和Applicative操作应涉及如下:
pure = return
最小的完整定义
(>>=)
请注意,最小定义仅需要>>=
,而不是return
,以及pure = return
(与所有此类“法律”一样,不能由语言强制执行但必须适用于所有“理智”实现的要求,否则语义将不正确)。
但有些类型是Applicative但不是Monad,因此有pure
但没有return
。 ZipList
是传统的例子。