Scala Future的成本是多少?

时间:2017-04-29 00:28:41

标签: scala future

scala Future的费用是多少?旋转起来,比如说只有1000个它们只能立即再次离开flatMap,这是不好的做法吗?

在我的情况下,我不需要 1000期货 - 我实际上可以逃脱约10个左右,但它使我的代码更清洁,使用更多的未来,我&#39 ; m试图在代码优雅和滥用资源之间进行权衡。显然,如果我有阻止代码,它们会很昂贵,但如果没有,我可以随意调整多少代码来保存几行代码?

2 个答案:

答案 0 :(得分:2)

你说你创建其中一些只是为了处理Future[T]的同类列表。在这种情况下,如果您只想将某些T提升为Future[T],则可以执行Future.successful(myValue)。这会导致执行无异步后台操作。它是一个现成的值,只包含在Future的上下文中。

编辑:重新阅读您的问题和评论后,我相信这足以得到答案。继续阅读以获取额外信息。

关于flatMapping,请注意,如果您事先创建1000个期货作为1000个不同的val,它们将立即开始(好吧,每当JVM执行上下文确定它是开始的好时机,但绝对是尽快)。但是,如果你在flatMap内部就地创建它们,它们将被链接(M-word的flatMap的整点是连续序列中的链接,每一步可能取决于前一个的结果)。

演示:

import scala.concurrent.{Await, Future}
import scala.concurrent.duration._
import scala.concurrent.ExecutionContext.Implicits.global

val f1 = Future({ Thread.sleep(2000); println("one") })
val f2 = Future({ Thread.sleep(2000); println("two") })

val result1 = f1.flatMap(f => f2)

Await.result(result1, 5 seconds)

val result2 = Future({ Thread.sleep(2000); println("one") })
  .flatMap(f => Future({ Thread.sleep(2000); println("two") }))

Await.result(result2, 5 seconds)

result1的情况下,你会在两秒钟后将“一”和“两”打印在一起(有时甚至是第一个“两个”然后“一个”)。但是在第二种情况下,我们在flatMap内部就地创建了期货,第一次“one”在两秒后打印,然后在另外两秒后打印“two”。这意味着如果您将1000个期货连为这样,但链条在步骤42中断,则其余的958期货将不会被计算。

通过结合关于期货的这两个事实,您可以避免创建不必要的事实。

我希望我至少帮助过一点,因为关于你的主要问题 - 未来需要多少内存和其他开销 - 我没有数字。这实际上取决于JVM的设置和运行代码的机器。但我确实认为,即使你的系统可以接受任何你投入的东西,你也不应该(很多)不必要的背景未来的计算。即使有合理的超时和通过各自的Promise取消这样的事情,创建额外的百万期货你将不需要听起来像一个糟糕的设计恕我直言。

(注意我说的是“背景计算”。如果你主要需要所有这些期货来保持所有类型“在未来的水平”,以便整个代码更容易使用(例如用于理解),在这种情况下前面提到的Future.successful是你的朋友,因为它不是计算,只是存储在Future上下文中的已经计算的值)

答案 1 :(得分:1)

我可能误解了你的问题。如果我弄错了,请纠正我。

  

scala Future的成本是多少?

每当你将来包装表达式a java runnable is created under the hood时。而Runnable只是一个run()的界面。然后,您的代码块将封装在runnable的run方法中。然后将此runnable提交给执行上下文。

从一般意义上说,未来只不过是一堆辅助方法可以运行。未来的实例与其他对象没有什么不同。您可以参考this thread来大致了解单个Java对象的内存消耗情况。

如果您有兴趣,可以从creation of a future

开始追踪整个行动链