【问题标题】:Must I implement Applicative and Functor to implement a Monad我必须实现 Applicative 和 Functor 来实现 Monad
【发布时间】:2015-07-02 21:36:50
【问题描述】:

我正在尝试实现一个 Monad 实例。作为一个更简单的例子,假设如下:

data Maybee a = Notheeng | Juust a 

instance Monad Maybee where
   return x = Juust x
   Notheeng >>= f = Notheeng
   Juust x >>= f = f x
   fail _ = Notheeng 

据我所知,这应该是 Maybe 的标准实现。但是,这不会编译,因为编译器会抱怨:

没有 (Applicative Maybee) 的实例

同样,一旦给出 Applicative,他想要一个 Functor 实例。

所以:一个简单的问题:在实现 Monad 之前我必须始终实现 Functor 和 Applicative 吗?

【问题讨论】:

  • 我预计在 GHC 7.10 发布之后会有很多关于此的问题。我们应该创建一个 Functor-Applicative-Monad 提案 标签吗?

标签: haskell monads functor applicative fam-proposal


【解决方案1】:

是的,以前不是这样,这是在 ghc7.10 中以Functor-Applicative-Monad Proposal 的名义引入的变化。

【讨论】:

    【解决方案2】:

    必须为FunctorApplicative 定义实例(第二个是较新版本的 Haskell 中的新要求),但实际上没什么大不了的,因为如果你不想手写你的自己的实例,您可以只使用这些实例:

    import Control.Applicative (Applicative(..))
    import Control.Monad       (liftM, ap)
    
    -- Monad m
    
    instance Functor m where
        fmap = liftM
    
    instance Applicative m where
        pure  = return
        (<*>) = ap
    

    【讨论】:

      【解决方案3】:

      对于 GHC 7.10 及更高版本,您必须实现 FunctorApplicativeMonad 的类定义要求超类实例:

      class Functor f => Applicative f where ...
      class Applicative m => Monad m where ...
      

      请注意,一旦您拥有了 Monad 实例,就可以轻松定义 FunctorApplicative 实例:

      import Control.Monad
      
      -- suppose we defined a Monad instance:
      instance Monad m where ...
      
      instance Functor m where
          fmap = liftM
      
      instance Applicative m where
          pure = return
          (<*>) = ap
      

      【讨论】:

      • 实际上不正确:在 7.8 及更早版本中,Monad 没有任何超类约束。
      • 呃,我犯了一个严重的错误。
      • 实现pure = return 不是一个好主意,我不认为。 return 有可能最终会消失,IIRC 甚至还有一个警告可用于发现 return 何时被实现为 pure 以外的任何东西。
      猜你喜欢
      • 2019-06-30
      • 1970-01-01
      • 1970-01-01
      • 2012-01-29
      • 2012-11-12
      • 1970-01-01
      • 2011-11-05
      相关资源
      最近更新 更多