自己動手擴展 Either 的 flatMap

大家知道在2.11版的scala中Either 沒有 flatMap

如何自己用隱式類型手動加一個呢?

看好如下

implicit final class EitherShip[+E, +A](val self: Either[E, A]) {
  def flatMap[EE >: E, B](f: A => Either[EE, B]): Either[EE, B] =
    self match {
      case Left(e) => Left(e)
      case Right(a) => f(a)
    }
}

就可以啦

測試一下

type Step = Int => Either[RuntimeException,Int]

val successfulSteps: Seq[Step] = List(
  (i:Int) => Right(i + 5),
  (i:Int) => Right(i + 10),
  (i:Int) => Right(i + 25))
val partiallySuccessfulSteps: Seq[Step] = List(
  (i:Int) => Right(i + 5),
  (i:Int) => Left(new RuntimeException("FAIL!")),
  (i:Int) => Right(i + 25))

def sumCounts1(countSteps: Seq[Step]): Either[RuntimeException,Int] = {
  val zero: Either[RuntimeException,Int] = Right(0)
  (countSteps foldLeft zero) {
    (sumEither, step) => sumEither flatMap (i => step(i))
  }
}

assert(sumCounts1(successfulSteps) == Right(40))

sumCounts1(partiallySuccessfulSteps) match {
  case Left(re) => assert(re.getMessage == "FAIL!")
  case Right(i) => assert(false, s"Should have failed, but returned $i")
}

very ok!

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章