2

これは私の前の質問へのフォローアップです:

次のような関数をリファクタリングしているとします。

def check(ox: Option[Int]): Unit = ox match {
  case None => throw new Exception("X is missing")
  case Some(x) if x < 0 => throw new Exception("X is negative")
  case _ => ()
}

または例外doCheckを返す新しい純粋関数を作成しています。Unit

case class MissingX() extends Exception("X is missing")
case class NegativeX(x: Int) extends Exception(s"$x is negative")

import scalaz._, Scalaz._

type Result[A] = Excepiton \/ A

def doCheck(ox:Option[Int]): Result[Unit] = for {
  x <- ox toRightDisjunction MissingX()
  _ <- (x >= 0) either(()) or NegativeX(x)
} yield ()

そしてそれを呼び出すcheck

def check(ox:Option[Int]): Unit = doCheck(ox) match {
  case -\/(e) => throw e
  case _ => ()
}

それは理にかなっていますか?そのように実装した方が良いでしょうdoCheckか?

def doCheck(ox:Option[Int]): Result[Int] = for {
  x1 <- ox toRightDisjunction MissingX()
  x2 <- (x1 >= 0) either(x1) or NegativeX(x1)
} yield x2

で実装する方法はcats

4

1 に答える 1

2

cat でもほとんど同じことを行いますが、cats 自体にはfrom scalazBoolean => Xor[A, B]のような構文がないだけです。either () or ()

import cats.data.Xor
import cats.implicits._

def doCheck(ox: Option[Int]): Xor[Exception, Unit] =
  ox.toRightXor(MissingX()).flatMap(x => if(x > 0) ().right else NegativeX(x).left)

mouseを使用できます。これは、cats に対して同様の構文ヘルパーを提供します。

import com.github.benhutchison.mouse.boolean._

ox.toRightXor(MissingX()).flatMap(x => (x > 0).toXor(NegativeX(x), ()))

Xorこのようなことを行うメソッドもありensureますが、述語が成り立たない場合は要素にアクセスできません。xforが必要ない場合はNegativeX、次のように記述できます。

ox.toRightXOr(MissingX()).ensure(Negative())(_ > 0).void
于 2016-06-20T07:10:49.300 に答える