如何绕过Haskell中的现有实例(for Failure)?

时间:2014-03-21 12:04:50

标签: haskell monad-transformers

我在使用IO的monad变换器中,我想为Failure定义我自己的实例。

因为Failure已经为IO和MonadTrans定义了实例,所以我甚至无法构建自己的重叠实例。

据我所知,我还有四个选择:

  1. Newtyping IO:
    这有点尴尬,我需要得出所有我想改变的东西,然后重新定义其余部分。
  2. 黑客未能将类本身分成它自己的模块:
    我将类定义移动到子模块Control.Failure.Class
  3. 为失败创建简单包装模块而不重新导出实例
  4. 从我的Monad Transformer中删除MonadTrans
  5. 你知道其他选择吗?你觉得怎么样?

1 个答案:

答案 0 :(得分:7)

newtype包装器是解决此类问题的标准方法。 GeneralizedNewtypeDeriving扩展名可以选择性地从包装的monad派生实例。

{-# LANGUAGE GeneralizedNewtypeDeriving #-}

-- | Your custom monad transformer
newtype YourMonadT e m r = 
  YourMonadT (EitherT e m r)
  -- Easily derive the instances using the GeneralizedNewtypeDeriving
  deriving (Functor, Applicative, Monad, MonadIO)

instance Failure e (YourMonadT e m) where
  failure = error "TODO: implement me however you want"