【问题标题】:Computation with Futures avoiding Await method使用 Futures 计算避免 Await 方法
【发布时间】:2020-01-19 06:11:45
【问题描述】:

我有调用 computeParallel() 函数的函数,该函数调用 3 个 Futures F1,F2,F3 并返回 String 作为返回类型。

def computeParallel():String =
{

      val f1 = Future {  "ss" }
      val f2 = Future { "sss" }
      val f3 = Future { "ssss" }

      val result: Future[String] = for {
        r1 <- f1
        r2 <- f2
        r3 <- f3
      } yield (r1 + r2 + r3)

    Await.result(result,scala.concurrent.duration.Duration.Inf)



} 

使用 Await 收集聚合结果。但是人们说使用 Await 是一种不好的编码方式。

所以我使用了下面的一个。它返回 Unit 类型。

        result.onComplete {
          case Success(res) => return res
        }

因此,如果返回 Unit,我将无法打印任何内容。

有什么办法可以帮助我们解决这个问题吗

提前致谢

【问题讨论】:

  • 在这种情况下会承诺帮助吗?
  • 你需要做什么?打印什么?对结果做点什么?
  • 从这里收集后我必须将结果传递给其他函数
  • 那么只需 mapflatMapforeach 使用该功能您的未来。 - 你明白未来意味着异步计算吗,你等待的那一刻,你就破坏了它。所以通常所有的代码都应该适应异步的。但发生这种情况是因为你需要它,如果不是,你为什么首先使用期货?
  • 是的,就像@LuisMiguelMejíaSuárez 所说,您不需要计算,只需映射并将结果传递给另一个函数。 result.map(otherFunction(_)) 或只是 result.map(otherFunction)

标签: scala apache-spark user-defined-functions future futuretask


【解决方案1】:

如果computeParallel 必须返回String,则必须返回Await.result

“编码的好方法”是在你进入期货后立即使用它们。

def computeParallel(): Future[String] = {
  val f1 = Future {  "ss" }
  val f2 = Future { "sss" }
  val f3 = Future { "ssss" }

  for {
    r1 <- f1
    r2 <- f2
    r3 <- f3
  } yield (r1 + r2 + r3)
} 

computeParallel().map(result => ???)

return 通常不应该在 Scala 中使用。

onComplete 无济于事,因为它

在任意(未指定)线程上运行...

在它完成之前我们不会阻塞。

Difference between Await.result and futures.onComplete in Scala

承诺可以在未来完成,所以您将再次拥有Future[String] 而不是String

【讨论】:

  • 谢谢,如果我使用 .map() 或 Oncomplete 我没有得到任何结果。如果我尝试用这些函数打印一些东西,就像打印“List()”并从运行时退出
  • 如果我不得不提到 Thread.sleep() 。我不确定它将执行多少时间。
  • @Learnis 关于map 我无法回答,你没有用map 编写代码。关于Oncomplete,我已经说过回调在不同的线程上运行,computeParallel 之前完成。
  • @Learnis Thread.sleep() 被阻止,Await.result 被阻止
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2020-01-20
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多