这是代码示例:
type FailFast[A] = Either[List[String], A]
import cats.instances.either._
def f1:ReaderT[FailFast, Map[String,String], Boolean] = ReaderT(_ => Right(true))
def f2:ReaderT[FailFast, Map[String,String], Boolean] = ReaderT(_ => Right(true))
def fc:ReaderT[FailFast, Map[String,String], Boolean] =
for {
b1 <- f1
if (b1)
b2 <- f2
} yield b2
错误是:
错误:withFilter的(17,13)值不是的成员 cats.data.ReaderT [TestQ.this.FailFast,Map [String,String],Boolean] b1 <-f1
如何将f1与f2组成。仅当f1返回Right(true)时才应用f2。我是通过以下方式解决的:
def fc2:ReaderT[FailFast, Map[String,String], Boolean] =
f1.flatMap( b1 => {
if (b1)
f2
else ReaderT(_ => Right(true))
})
但是我希望有一个更优雅的解决方案。
答案 0 :(得分:1)
ReaderT[FailFast, Map[String, String], Boolean]
类型令人讨厌。我将其替换为ConfFF
-快捷方式(“映射配置的快速失败”);您可能会为此找到一个更好的名字。for
理解语法。_ =>
和Right(...)
,只需使用pure
中合适的applicative
。因此,您的fc2
变为:
def fc3: ConfFF[Boolean] =
for {
b1 <- f1
b2 <- if (b1) f2 else true.pure[ConfFF]
} yield b2
完整代码:
import scala.util.{Either, Left, Right}
import cats.instances.either._
import cats.data.ReaderT
import cats.syntax.applicative._
object ReaderTEitherListExample {
type FailFast[A] = Either[List[String], A]
/** Shortcut "configured fail-fast" */
type ConfFF[A] = ReaderT[FailFast, Map[String, String], A]
def f1: ConfFF[Boolean] = ReaderT(_ => Right(true))
def f2: ConfFF[Boolean] = ReaderT(_ => Right(true))
def fc3: ConfFF[Boolean] =
for {
b1 <- f1
b2 <- if (b1) f2 else true.pure[ConfFF]
} yield b2
}