Ниже вы можете найти способ адаптации монады состояния кошки к вашему случаю.Однако у меня были некоторые проблемы с секвенированием List[State[S, A]]
, чтобы у кошек было State[S, List[A]]
, поэтому я написал для этого функцию sequence
.Если бы кто-то знал, как это сделать, мне было бы интересно:)
import cats.data._
case class Foo(x: Double)
def bar(y: Double): State[Foo, Double] = for {
foo <- State.get[Foo]
_ <- State.set(Foo(foo.x + y))
} yield foo.x / (foo.x + y)
val xs: List[State[Foo, Double]] = List(1.0, 2.0, 3.0, 4.0).map(bar)
def sequence(xs: List[State[Foo, Double]]): State[Foo, List[Double]] =
xs.foldLeft(State.pure[Foo, List[Double]](List.empty[Double])) { (acc, x) =>
for {
xs <- acc
xx <- x
} yield xx :: xs
}
val s = sequence(xs)
val ss = s.map(_.head)
s.run(Foo(0)).value
ss.run(Foo(0)).value
ss.flatMap(_ => bar(3)).run(Foo(0)).value
В результате вы получите
res0: (Foo, List[Double]) = (Foo(10.0),List(0.6, 0.5, 0.3333333333333333, 0.0))
res1: (Foo, Double) = (Foo(10.0),0.6)
res2: (Foo, Double) = (Foo(13.0),0.7692307692307693)