如何在List [F [G [A]]]上运行序列得到F [G [List [A]]]

Noe*_*l M 7 scala scalaz

是否有可能很好地转变List[F[G[A]]]成一个F[G[List[A]]]

我可以通过以下方式在Scalaz中执行此操作:

val x: List[Future[Option[Int]]] = ???
val transformed: Future[Option[List[Int]]] = x.sequenceU.map(_.sequenceU)
Run Code Online (Sandbox Code Playgroud)

我只是想知道是否有更好的方法来做这个而不是.sequenceU.map(_.sequenceU)使用monad变换器?我确实尝试了这个,没有太多运气.

Tra*_*own 5

如果你想避免嵌套测序,Monad变换器是你要走的路.在这种情况下,你想要一个OptionT[Future, A](相当于Future[Option[A]]):

import scalaz._, Scalaz._
import scala.concurrent.ExecutionContext.Implicits.global
import scala.concurrent.Future

val xs = List(OptionT(Future(some(1))), OptionT(Future(some(2))))
val ys = OptionT(Future(none[Int])) :: xs

val sequencedXs: Future[Option[List[Int]]] = xs.sequenceU.run
val sequencedYs: Future[Option[List[Int]]] = ys.sequenceU.run
Run Code Online (Sandbox Code Playgroud)

然后:

scala> sequencedXs.foreach(println)
Some(List(1, 2))

scala> sequencedYs.foreach(println)
None
Run Code Online (Sandbox Code Playgroud)

正如所料.