Scala: для понимания с охраной внутри читателя - PullRequest
2 голосов
/ 27 марта 2019

Вот пример кода:

  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

Ошибка:

Ошибка: (17, 13) значение withFilter не является членом cats.data.ReaderT [TestQ.this.FailFast, карта [String, String], Boolean] b1 <- f1 </p>

Как мне составить f1 с помощью f2. f2 должен применяться только если f1 возвращает Right (true). Я решил это через:

  def fc2:ReaderT[FailFast, Map[String,String], Boolean] =
    f1.flatMap( b1 => {
      if (b1)
        f2
      else ReaderT(_ => Right(true))
    })

Но я надеюсь, что есть более элегантное решение.

1 Ответ

1 голос
/ 27 марта 2019
  1. Огромный тип ReaderT[FailFast, Map[String, String], Boolean] раздражает. Я заменил его на ConfFF -shortcut («карта-настроенная сбоев-быстро»); Вы, вероятно, можете найти лучшее название для этого.
  2. Вы по-прежнему можете использовать синтаксис for, если хотите.
  3. Нет необходимости каждый раз записывать все _ => и 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
}
...