【问题标题】:Compute/parse list elements (links) in parallel并行计算/解析列表元素(链接)
【发布时间】:2013-08-14 17:12:41
【问题描述】:

无法理解并行计算列表元素的正确方法是什么,但是在不计算元素时阻塞主线程(并行)。用例:我有一个 URL 链接列表和一个简单的 html 页面解析器,我如何通过并行解析每个页面来减少从给定页面获取信息所需的时间,然后返回一个包含一些 JSON 数据的简单列表.

据我所知,我有两种选择:

与 Futures 的并发方式

我有一个方法可以在 Future 中提取一些 JSON 数据:

def extractData(link: String): Future[JValue] = // some implementation

我只是将它映射到链接列表上,该类型将是 List[Future[JValue]]:

val res: List[Future[JValue]] = listOfLink.map(extractData)

如果我调用 sequence(例如来自 Scalaz,或我自己的实现)遍历此列表并将其转换为 Future[List[JValue]],则链接仍将按顺序处理,但单独的线程不会给出我有任何效率,因为结果我需要得到一个List[JValue]

尝试使用 ParSeq 进行计算

在这个选项中,我有一个只提取数据的函数:

def extractData(link: String): JValue = // some implementation

但这次在集合上调用.par

val res: ParSeq[JValue] = listOfLinks.map(extractData)

但是通过这种方式,我不太明白如何在不计算孔列表的情况下阻塞主线程,而不按顺序解析每个链接

至于 Akka,我只是不能在这里使用演员,所以只能使用 FuturePar*

【问题讨论】:

  • 当我在ParIterableLike类中查看map函数的实现时,上面写着...tasksupport.executeAndWaitResult...。我不了解所有细节,但这可能意味着该线程已经被此实现阻塞。使用Futures 的另一种方法是flatMap 而不是map,将单个Futures 组合成一个Future,当所有“小”Futures 都准备好时,该Future 就准备好了。我不能肯定地说,因为我也在学习 scala,提出了同样的问题。 ;) 祝你好运。

标签: parsing scala concurrency parallel-processing concurrent-programming


【解决方案1】:

当您将extractData 映射到集合时,链接并行处理。考虑一个稍微简化的例子:

import scala.concurrent._
import ExecutionContext.Implicits.global

def extractData(s: String) = future {
  printf("Starting: %s\n", s)
  val i = s.toInt
  printf("Done: %s\n", s)
  i
}

val xs = (0 to 5).map(_.toString).toList

val parsed = Future.sequence(xs map extractData)

现在您将看到类似以下内容,这清楚地表明这些事情不是按顺序处理的:

Starting: 0
Done: 0
Starting: 2
Done: 2
Starting: 1
Starting: 4
Done: 1
Starting: 3
Starting: 5
Done: 5
Done: 4
Done: 3

请注意,您可以使用Future.traverse 来避免创建期货的中间列表:

val parsed = Future.traverse(xs)(extractData)

无论哪种情况,您都可以使用Await 阻止:

val res = Await.result(parsed, duration.Duration.Inf)

作为脚注:我不知道您是否打算使用Dispatch 来执行 HTTP 请求,但如果没有,那么值得一看。它还提供了很好的集成 JSON 解析,并且文档中充满了如何使用期货的有用示例。

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 2017-10-31
    • 1970-01-01
    • 2022-10-17
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2015-07-19
    • 1970-01-01
    相关资源
    最近更新 更多