在 haskell 中定义一个新的 monad 不会引发 Applicative 的实例
Defining a new monad in haskell raises no instance for Applicative
我正在尝试定义一个新的 monad,但出现了一个奇怪的错误
newmonad.hs
newtype Wrapped a = Wrap {unwrap :: a}
instance Monad Wrapped where
(>>=) (Wrap x) f = f x
return x = Wrap x
main = do
putStrLn "yay"
$ ghc --version
The Glorious Glasgow Haskell Compilation System, version 7.10.1
$ ghc newmonad.hs
[1 of 1] Compiling Main ( newmonad.hs, newmonad.o )
newmonad.hs:2:10:
No instance for (Applicative Wrapped)
arising from the superclasses of an instance declaration
In the instance declaration for ‘Monad Wrapped’
为什么我需要定义一个Applicative
的实例?
这是 Applicative Monad Proposal (AMP)。现在,每当您将某些内容声明为 Monad
时,您还必须将其声明为 Applicative
(因此 Functor
)。从数学上讲,每个 monad 都是 一个应用函子,所以这是有道理的。
您可以执行以下操作来消除错误:
instance Functor Wrap where
fmap f (Wrap x) = Wrap (f x)
instance Applicative Wrap where
pure = Wrap
Wrap f <*> Wrap x = Wrap (f x)
https://wiki.haskell.org/Functor-Applicative-Monad_Proposal
编辑: 也许我应该更清楚地指出这是 最近 的事情?您发布的代码以前可以工作,但是使用 最新 版本的 GHC 时会出现错误。这是一个突破性的变化。
编辑: 以下声明适用于 any monad:
import Control.Applicative -- Otherwise you can't do the Applicative instance.
import Control.Monad (liftM, ap)
instance Functor ??? where
fmap = liftM
instance Applicative ??? where
pure = return
(<*>) = ap
根据所讨论的 monad,可能会有更高效的实现,但这是一个简单的起点。
最规范化和最不引人注目的答案是:-
因为 Monad 依赖于 Applicative
class Applicative m => Monad m where ...
Applicative 依赖于 Functor
class Functor f => Applicative f where ...
我们需要实例定义
> instance Functor Wrapped where
> fmap = liftM
和
> instance Applicative Wrapped where
> pure = return
> (<*>) = ap
我正在尝试定义一个新的 monad,但出现了一个奇怪的错误
newmonad.hs
newtype Wrapped a = Wrap {unwrap :: a} instance Monad Wrapped where (>>=) (Wrap x) f = f x return x = Wrap x main = do putStrLn "yay"
$ ghc --version The Glorious Glasgow Haskell Compilation System, version 7.10.1 $ ghc newmonad.hs [1 of 1] Compiling Main ( newmonad.hs, newmonad.o ) newmonad.hs:2:10: No instance for (Applicative Wrapped) arising from the superclasses of an instance declaration In the instance declaration for ‘Monad Wrapped’
为什么我需要定义一个Applicative
的实例?
这是 Applicative Monad Proposal (AMP)。现在,每当您将某些内容声明为 Monad
时,您还必须将其声明为 Applicative
(因此 Functor
)。从数学上讲,每个 monad 都是 一个应用函子,所以这是有道理的。
您可以执行以下操作来消除错误:
instance Functor Wrap where
fmap f (Wrap x) = Wrap (f x)
instance Applicative Wrap where
pure = Wrap
Wrap f <*> Wrap x = Wrap (f x)
https://wiki.haskell.org/Functor-Applicative-Monad_Proposal
编辑: 也许我应该更清楚地指出这是 最近 的事情?您发布的代码以前可以工作,但是使用 最新 版本的 GHC 时会出现错误。这是一个突破性的变化。
编辑: 以下声明适用于 any monad:
import Control.Applicative -- Otherwise you can't do the Applicative instance.
import Control.Monad (liftM, ap)
instance Functor ??? where
fmap = liftM
instance Applicative ??? where
pure = return
(<*>) = ap
根据所讨论的 monad,可能会有更高效的实现,但这是一个简单的起点。
最规范化和最不引人注目的答案是:-
因为 Monad 依赖于 Applicative
class Applicative m => Monad m where ...
Applicative 依赖于 Functor
class Functor f => Applicative f where ...
我们需要实例定义
> instance Functor Wrapped where
> fmap = liftM
和
> instance Applicative Wrapped where
> pure = return
> (<*>) = ap