使错误适应 [英] Adapting Error to Except

查看:65
本文介绍了使错误适应的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

现在已弃用 Control.Monad.Error ,而 Control.Monad.Except 占据上风的在线资源还没有赶上,仍然显示了如何使用 Error 的示例。

Now that Control.Monad.Error is deprecated, and Control.Monad.Except reigns supreme, a lot of sources online haven't caught up, and still show examples of how to use Error.

我要转身

instance Error MyError where
  noMsg  = ...
  strMsg = ...

使用转换为某些内容。只是将 Error 替换为 Except 并不能用作 Except 希望有其他类型参数

into something using Except. Just replacing Error with Except didn't work as Except expects additional type parameters

我知道中不存在那些确切的方法,所以有什么替代方法?

I understand that those exact methods don't exist in Except, so what's the alternative?

推荐答案

简单的答案是:根本不替换 Error ,替换 ExceptT ErrorT ,只要您不使用,事情就应该继续起作用错误的方法,失败(现在具有不同的定义),或者 do 表示法。

Short answer is: Replace Error by nothing at all, replace ErrorT by ExceptT, and things should continue to work as long as you don't use Errors methods, fail (which now has a different definition), or failing pattern matches in do notation.

旧的 Control.Monad.Error 系统与新的 Control.Monad.Except 系统是新系统对错误/异常类型施加了 no 类限制。

The essential difference between the old Control.Monad.Error system and the new Control.Monad.Except system is that the new system imposes no class restriction on the error/exception type.

已发现,多态地使用任何错误/异常类型的能力比有点黑的ab更为有用。

It was found that the ability to use any error/exception type at all, polymorphically, was more useful than the somewhat hacky ability to customize conversion of string error messages.

因此,类 Error 完全消失了。

作为副作用, ExceptT 失败现在从底层被解除单子。这也改变了 do 表示法失败模式的影响。

As a side effect, fail for ExceptT now is lifted from the underlying monad. This also changes the effect of failing patterns in do notation.

旧定义是:

fail msg = ErrorT $ return (Left (strMsg msg))

我认为等同于

fail msg = throwError (strMsg msg)

如果您仍然需要此行为,则可以改用

If you still need this behavior, you can instead use

throwError yourIntendedErrorValue

变形金刚(即 Control.Monad.Trans.Except throwE 可以工作c>)而不是 mtl 。)

(throwE works instead if you're using transformers (i.e. Control.Monad.Trans.Except) rather than mtl.)

旧的模式匹配失败将适用于

The old do pattern matching failure would apply to things like

do
    Just x <- myErrorTAction
    ...

当操作实际返回 Nothing 。这比较尴尬,但是您可以例如将其替换为明确的情况匹配(基本上是废话):

when the action actually returns Nothing. This is more awkward, but you could e.g. replace it with an explicit case match (essentially desugaring it):

do
    y <- myErrorTAction
    case y of
        Nothing -> throwE ...
        Just x -> do
           ...

@DanielWagner建议采取以下措施以避免缩进:

@DanielWagner suggests the following to avoid extra indentation:

do
    x <- myErrorTAction >>= maybe (throwError ...) return
    ...

错误的消除也消除了需要对于 Control.Monad.Error 的命名不一致:大多数转换器遵循 SomethingT 是转换器,而 Something SomethingT ... Identity 的类型别名。旧的 ErrorT 打破了这一点,因为 Error 类用于完全不同的东西。

The removal of Error also eliminates the need for an inconsistency in naming that Control.Monad.Error had: Most transformers follow the rule that SomethingT is the name of the transformer, and Something is a type alias for SomethingT ... Identity. The old ErrorT broke that because the Error class was used for something entirely different.

在新系统中, Except e = ExceptT e Identity ,就像其他变压器一样。

In the new system, Except e = ExceptT e Identity, like for other transformers.

这篇关于使错误适应的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆