问题标签 [either]

For questions regarding programming in ECMAScript (JavaScript/JS) and its various dialects/implementations (excluding ActionScript). Note JavaScript is NOT the same as Java! Please include all relevant tags on your question; e.g., [node.js], [jquery], [json], [reactjs], [angular], [ember.js], [vue.js], [typescript], [svelte], etc.

0 投票
2 回答
3980 浏览

scala - Try[Result], IO[Result], Either[Error,Result],到底应该用哪个

我想知道我的方法的签名应该是什么,以便我优雅地处理不同类型的失败。

这个问题是我已经对 Scala 中的错误处理提出的许多问题的总结。你可以在这里找到一些问题:


目前,我了解以下内容:

  • 两者都可以用作可能失败的方法调用的结果包装器
  • Try 是偏右的 Either,失败是非致命的异常
  • IO (scalaz) 有助于构建处理 IO 操作的纯方法
  • 所有 3 个都可以在理解中轻松使用
  • 由于不兼容的 flatMap 方法,所有 3 个都不容易在 for 理解中混合
  • 在函数式语言中,我们通常不会抛出异常,除非它们是致命的
  • 我们应该在非常特殊的情况下抛出异常。我想这是 Try 的方法
  • 创建 Throwables 对 JVM 有性能成本,并且不打算用于业务流控制

存储层

现在请考虑我有一个UserRepository. UserRepository存储用户并定义findById方法。可能会发生以下故障:

  • 致命的失败(OutOfMemoryError )
  • IO 失败,因为数据库不可访问/不可读取

此外,用户可能会丢失,从而导致Option[User]结果

使用存储库、SQL 的 JDBC 实现,可以抛出非致命异常(违反约束或其他),因此使用 Try 是有意义的。

当我们处理 IO 操作时,如果我们想要纯函数,那么 IO monad 也是有意义的。

所以结果类型可能是:

  • Try[Option[User]]
  • IO[Option[User]]
  • 别的东西?

服务层

现在让我们介绍一个业务层,UserService它提供了一些updateUserName(id,newUserName)使用之前定义的方法findById的存储库的方法。

可能会发生以下故障:

  • 所有存储库故障都传播到服务层
  • 业务错误:无法更新不存在的用户的用户名
  • 业务错误:新用户名太短

那么结果类型可能是:

  • Try[Either[BusinessError,User]]
  • IO[Either[BusinessError,User]]
  • 别的东西?

这里的 BusinessError 不是 Throwable,因为它不是异常失败。


使用理解

我想继续使用 for-comprehensions 来组合方法调用。

我们不能轻易地在理解上混合不同的 monad,所以我想我应该为我的所有操作使用某种统一的返回类型,对吧?

我只是想知道,在现实世界的 Scala 应用程序中,当可能发生不同类型的故障时,您如何成功地继续使用 for-comprehensions。

现在,为了理解对我来说效果很好,使用所有返回Either[Error,Result]但所有不同类型的故障都融合在一起的服务和存储库,处理这些故障变得有点笨拙。

您是否定义了不同类型的 monad 之间的隐式转换以便能够用于理解?

您是否定义了自己的 monad 来处理故障?

顺便说一句,也许我很快就会使用异步 IO 驱动程序。所以我想我的返回类型可能更复杂:IO[Future[Either[BusinessError,User]]]


任何建议都会受到欢迎,因为我真的不知道该使用什么,而我的应用程序并不花哨:它只是一个 API,我应该能够区分可以显示给客户端的业务错误,以及技术错误。我试图找到一个优雅而纯粹的解决方案。

0 投票
1 回答
134 浏览

scala - 当使用 EitherT[StateWithSomeFixedStateType, T, U] 时,当返回 left 时如何进行一些状态操作?

假设您有一个看起来像这样的 EitherT:

如果您有一个可以返回左的理解:

你如何跟进一个在自身返回左侧之前操纵状态的理解?

我想我想要一些非常接近 orElse 的东西,但是 orElse 无法访问左侧的值:

如果它需要像 (x: => Int => EitherT[F, AA, BB]) 而不是仅仅 (x: => EitherT[F, AA, BB]),它会起作用。

我曾尝试从:

但是如果我从调用 isLeft 开始,看起来计算至少运行了两次,一次是为 isLeft,一次是在我调用 leftMap 之类的东西时。

在这里使用什么是正确的?

0 投票
4 回答
1095 浏览

haskell - 是否可以在单子序列中更改单子类型?

我知道可以更改包装类型,以便您可以拥有

但有可能改变m吗?如果mis a MonadErrorand 由 an Either ErrorAand实现Either ErrorB,我可以以某种方式链接它们吗?显然我不能直接将它们链接起来,因为 的类型是Left什么?但是,无论哪种情况,我最终都会打电话show,但我没有找到比这更好的解决方案

它无法正确使用在第一个错误处停止的单子行为,而无需我进行明确检查。

0 投票
3 回答
4772 浏览

scala - Scala.Either orElse 方法

Either在 Scala 中使用 's 的惯用方式是什么?例如,当使用OptionI时orElse,如果 current 为 ,则可以使用方法获取下一个可选值None。但是如何以Either同样的方式工作呢?我没有找到像orElse 链接 Either's 的方法(而且我知道拥有这种方法并不是一个好主意,因为我们失去了Left价值)

编辑:事实上,我有一个if-elseif-elseif-else表达式序列,每个都返回Rightor Left。我想重构我的代码,让它变得“更实用”。firstOption orElse secondOption orElse...所以我可以用if来替换它Option,但是如何在这里使用Either呢?

0 投票
1 回答
3424 浏览

scala - Scala.Either getOrElse 方法

为什么当我输入这一切都很好?

但是当我输入这个编译失败?

编译错误:

value getOrElse 不是 java.io.Serializable
println(RightString, Int.left getOrElse RightString, Int.left getOrElse LeftString, Int)的成员

所以我不能链接getOrElse方法调用

0 投票
2 回答
3416 浏览

scala - 模式匹配

Scala 中的函数式编程,我正在尝试实现Either.map.

除其他外,编译时出现一个错误。我没有展示它们,因为我似乎缺少实施的概念Either.

请告诉我实施它。

0 投票
3 回答
1506 浏览

scala - Scala 中的链式验证

我有一个case class包含命令行配置信息的 Scala:

我正在编写一个验证函数来检查每个值是否为Some

但是如果我理解 Haskell 的 monad,似乎我应该能够将验证链接在一起(伪语法):

如果任何config.XXX表达式返回Failure,整个事情 ( validateConfig) 应该失败,否则Success(config)应该返回。

有没有办法用Try或者其他类来做到这一点?

0 投票
2 回答
1666 浏览

scala - 在 Scala 中结合 Futures (Twitter) 和 Either

我们使用 Twitter 期货(作为 Finagle 堆栈的一部分),我不喜欢使用(业务)异常来控制应用程序流的概念,因为异常不会出现在方法签名中。

所以我有了用 Future[Either[A,B]] 作为替代的想法。

但是我在使用这个概念对期货进行理解时遇到了一些问题:

例如,我们有一个存储库方法:

和一个处理程序方法,它使用这个 repo 并执行一些其他检查并创建一个令牌

getUserCredentialsByNickname(..) 之后的 for comprehension 中的调用仅应在此调用返回 Right[UserCredentials] 时执行,而且每个返回的 Either 的详细错误信息也应从处理程序返回。

0 投票
2 回答
3028 浏览

scala - 用于 if 守卫的理解

如何使用 if guard 进行推导?

我在使用它时遇到了这个错误。

编辑: 我遇到了另一个错误。我认为如果使用防护,它会返回一个选项结果。

编辑2

0 投票
2 回答
314 浏览

scala - 对于 if guard throws error 的理解

当我以这种方式使用 if guard 进行理解时出现一个错误。

代码:

错误: