【问题标题】:Future[Option[Future[Int]]] to Future[Option[Int]]Future[Option[Future[Int]]] 到 Future[Option[Int]]
【发布时间】:2015-11-03 03:11:41
【问题描述】:

Scala 中从Future[Option[Future[Int]]] 转换为Future[Option[Int]] 的最简洁方法是什么?有没有可能?

【问题讨论】:

  • 如果你决定走 scalaz 路线,这就是 monad 转换器擅长的事情。我认为OptionT[Task, Int] 会在这里为您提供帮助。相关:stackoverflow.com/a/14386670/402884

标签: scala future


【解决方案1】:

您可以将两个嵌套的Futures 合并为一个,因此这需要flatMap

def flatten[A](f: Future[Option[Future[A]]]): Future[Option[A]] =
  f.flatMap({
    case None => Future.successful(None)
    case Some(g) => g.map(Some(_))
  })

或者,更简洁:

def flatten[A](f: Future[Option[Future[A]]]): Future[Option[A]] =
  f.flatMap(o => Future.sequence(o.toSeq).map(_.headOption))

感谢@lmm 对此想法的回答。理想情况下,这可以写成f.flatMap(Future.sequence),但不幸的是sequence 需要TraversableOnce,而Option 没有扩展。

【讨论】:

    【解决方案2】:

    最干净的方法可能是使用scalaz:

    import scalaz.std.option._
    import scalaz.std.scalaFuture._
    import scalaz.syntax.traverse._
    
    //assuming implicit execution context in scope
    
    f.flatMap(_.sequence)
    

    【讨论】:

      【解决方案3】:

      您正在询问如何编写代码从某个纸袋中出来,并且您已经得到了一些关于如何做到这一点的好答案,但是您应该退后一步,尽量不要进入您当前所在的纸袋. 在这里查看我的答案:Get rid of Scala Future nesting 关于如何避免进入 Future[X[Future[y]] 类型签名,这样您就不必弄清楚如何摆脱它。

      【讨论】:

        猜你喜欢
        • 1970-01-01
        • 1970-01-01
        • 2016-11-08
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 2020-03-16
        • 1970-01-01
        • 1970-01-01
        相关资源
        最近更新 更多