标签: scala-cats

折叠在NonEmptyList上

我正在尝试使用猫库,但我很难在导入和创建的东西之间导航.我的问题如下:

sealed trait Checks
case class CheckViolation(id: Long, msg: String) extends Checks
case class ChecksPassed(ids: Seq[Long]) extends Checks
Run Code Online (Sandbox Code Playgroud)

这是我想要使用的数据结构.每个违规都应该作为具有msg的对象保存,传递的检查可以聚合为仅保存id.

object BusinessRuleSetValidation extends App {

  type BRValidationResult = Validated[NonEmptyList[CheckViolation], ChecksPassed]

  def run(): BRValidationResult = {

    implicit val monoidChecksPassed = new Monoid[ChecksPassed] {
      override def empty: ChecksPassed = ChecksPassed(Seq())

      override def combine(x: ChecksPassed, y: ChecksPassed): ChecksPassed = ChecksPassed(x.ids ++ y.ids)
    }



    val check1: BRValidationResult = valid(ChecksPassed(2L))
    val check2: BRValidationResult = invalidNel(CheckViolation(1, "This check was violated"))
    val check3: BRValidationResult = invalidNel(CheckViolation(2, "This is …
Run Code Online (Sandbox Code Playgroud)

scala scala-cats

5
推荐指数
1
解决办法
708
查看次数

堆叠M,Either和Writer

我目前正在使用EitherT堆叠Futures和Eithers:

type ErrorOr[A] = Either[Error, A]

def getAge: Future[ErrorOr[Int]] = ???
def getDob(age: Int): ErrorOr[LocalDate] = ???

for {
  age <- EitherT(getAge)
  dob <- EitherT.fromEither[Future](getDob(age))
} yield dob
Run Code Online (Sandbox Code Playgroud)

我现在想介绍一下Writer monad ie

type MyWriter[A] = Writer[Vector[String], ErrorOr[A]]

def getAge: Future[MyWriter[Int]] = ???
def getDob(age: Int): MyWriter[LocalDate] = ???
Run Code Online (Sandbox Code Playgroud)

我的问题是,对调用getAgegetDob调用进行排序的最佳方法是什么?我知道monads可以堆叠,Future -> Writer -> Either但是我可以继续EitherT在这种情况下使用吗?如果是这样的话?

monads scala monad-transformers scala-cats

5
推荐指数
2
解决办法
368
查看次数

无法在cat库中调用map方法

我正在阅读高级Scala With Cats.我在函子描述(第59页)中坚持这个例子:

object FunctorsDemo extends App {

  import cats.instances.function._
  import cats.syntax.functor._

  val func1 = (x: Int) => x.toDouble
  val func2 = (y: Double) => y * 2

  val func3 = func1.map(func2) // wrong line for me

}
Run Code Online (Sandbox Code Playgroud)

在书中一切都很好,但我有这个例外:

Error:(10, 21) value map is not a member of Int => Double
  val func3 = func1.map(func2)
Run Code Online (Sandbox Code Playgroud)

无法理解我做错了什么.

scala scala-cats

5
推荐指数
1
解决办法
126
查看次数

如何将ADT列表分类为其变体?

是否有可能以某种方式将解决方案扩展为总和类型?

sealed trait Group
case class A extends Group
case class B extends Group
case class C extends Group
def divide(l : List[Group]): //Something from what I can extract List[A], List[B] and List[C]
Run Code Online (Sandbox Code Playgroud)

functional-programming scala scalaz scala-cats

5
推荐指数
1
解决办法
120
查看次数

用猫创建抽象集合的有效方法

我有一些使用Monix Observable进行文件流处理的代码.为了测试这段代码,我希望我所做的操作Observable是独立的,所以我也可以在任何其他数据结构上执行它们List.这就是我编写以下代码来抽象底层数据结构的原因:

def permutations[F[_] : Applicative : FunctorFilter : SemigroupK](chars: F[Char]): F[F[Char]] = {
  Range.inclusive('a', 'z').map(_.toChar)
    .map { c ?
      FunctorFilter[F].filter(chars)(Character.toLowerCase _ andThen (_ != c))
    }
    .map(Applicative[F].pure)
    .reduceLeft(SemigroupK[F].combineK)
}
Run Code Online (Sandbox Code Playgroud)

让我烦恼的是,这段代码创建了许多中间数据结构.是否有我可以使用的类型类使这个过程更有效?将一个数据结构提升到另一个数据结构而没有太多开销的东西,比如LiftIO项目集合?

scala scala-cats monix

5
推荐指数
1
解决办法
136
查看次数

如何使用IO monad在猫中撰写理解力

我有以下代码:

import cats.effect.IO
import cats.data.State
import cats.data.StateT
import cats.implicits._
import cats.effect.LiftIO

abstract class Example {
    object implicits {
        implicit def myEffectLiftIO: LiftIO[IOGameplay] =
            new LiftIO[IOGameplay] {
                override def liftIO[A](ioa: IO[A]): IOGameplay[A] = {
                    StateT.liftF(ioa)
                }
            }
    }

    type Gameplay[A] = State[GameState, A]
    type IOGameplay[A] = StateT[IO, GameState, A]
    type EitherDirection[A] = Either[Throwable, A]

    type Map = Array[Array[FieldType]]
    sealed trait FieldType
    case class GameState(map: Map, block: Block)
    case class Block(f1: Field, f2: Field) 
    case class Field()

    import implicits._
    val L = …
Run Code Online (Sandbox Code Playgroud)

scala scala-cats cats-effect

5
推荐指数
1
解决办法
103
查看次数

EitherT:仅当满足特定条件时,调用函数才返回Either(否则返回右)

因此,我有一个特定的函数,只有在特定条件为真时才需要调用。如果它是错误的,我认为它是正确的。

我将使用EitherT.cond,但问题是我函数的返回类型是Future [Either [ErrorType,Unit]],所以它不适合我。这是我想要的代码:

def callEitherFunction: Future[Either[ErrorType, Unit]]

for {
_ <- if (condition) {
     EitherT(callEitherFunction)
   } else {
     Either.right[ErrorType, Unit](()).toEitherT[Future]
   }
} yield {
  //Some actions
}
Run Code Online (Sandbox Code Playgroud)

我想知道是否有更优雅的方法。将不胜感激。

scala monad-transformers either conditional-statements scala-cats

5
推荐指数
1
解决办法
115
查看次数

flatMap 忽略结果

我想知道是否存在一个函数(在 scala 或猫中)忽略flatMap. 例如

Some("ignore this").ignoreArgumentFlatMap(Some("result"))
Run Code Online (Sandbox Code Playgroud)

这将与

Some("ignore this").flatMap(_ => Some("result"))
Run Code Online (Sandbox Code Playgroud)

monads scala scala-cats

5
推荐指数
1
解决办法
253
查看次数

在函数参数级别实现 Ad hoc 多态性(混合不同类型的参数)

当我在 Scala 中有一个函数时:

def toString[T: Show](xs: T*): String = paths.map(_.show).mkString
Run Code Online (Sandbox Code Playgroud)

以及范围内的以下类型类实例:

implicit val showA: Show[MyTypeA]
implicit val showB: Show[MyTypeB]
Run Code Online (Sandbox Code Playgroud)

我可以通过toString以下方式使用函数:

val a1: MyTypeA
val a2: MyTypeA
val stringA = toString(a1, a2)

val b1: MyTypeB
val b2: MyTypeB
val stringB = toString(b1, b2)
Run Code Online (Sandbox Code Playgroud)

但我不能叫toString混合型的参数MyTypeAMyTypeB

// doesn't compile, T is inferred to be of type Any
toString(a1, b1)
Run Code Online (Sandbox Code Playgroud)

是否有可能以toString一种可以混合不同类型的参数(但仅限于Show类型类可用)的方式重新定义?

请注意,我知道 cat show interpolator 可以解决这个特定的例子,但我正在寻找一种也可以应用于不同情况的解决方案(例如toNumber)。

我也知道通过.show在将参数传递给toString …

polymorphism scala implicit typeclass scala-cats

5
推荐指数
2
解决办法
158
查看次数

为什么具有 Monad 实例的类型的 Semigroupal 不组合?

我正在尝试将我的头围绕在 Cats 中的 Semigroupals 上。以下是 Underscore 的“Scala with Cats”中的陈述。

cats.Semigroupal 是一个允许我们组合上下文的类型类

trait Semigroupal[F[_]] {
  def product[A, B](fa: F[A], fb: F[B]): F[(A, B)]
}
Run Code Online (Sandbox Code Playgroud)

参数fafb彼此独立:在将它们传递给 之前,我们可以按任一顺序计算它们product。这与 形成对比flatMap,后者对其参数施加了严格的顺序。

所以基本上,我们也应该能够结合两个Either上下文,但这似乎不起作用:

import cats.instances.either._ 

type ErrorOr[A] = Either[Vector[String], A]

Semigroupal[ErrorOr].product(Left(Vector("Error 1")), Left(Vector("Error 2")))

// res3: ErrorOr[Tuple2[Nothing, Nothing]] = Left(Vector("Error 1"))
Run Code Online (Sandbox Code Playgroud)

如果 semigroupal 的 USP 急切地执行独立操作,则必须在传递给之前对两者进行评估product,但我们无法获得组合结果。

我们可能期望product应用于Either累积错误而不是快速失败。同样,也许令人惊讶的是,我们发现它product实现了与 相同的 fail?fast 行为flatMap

这是否与使用替代方法能够组合任何相同类型的上下文的原始前提相悖?

为了确保一致的语义,Cats 的 Monad(它扩展了 Semigroupal)根据map …

scala scala-cats

5
推荐指数
1
解决办法
68
查看次数