Apache spark 在Spark映射分区中使用Java 8 parallelStream

Apache spark 在Spark映射分区中使用Java 8 parallelStream,apache-spark,parallel-processing,java-8,spark-streaming,Apache Spark,Parallel Processing,Java 8,Spark Streaming,我试图理解spark parallelism中Java8并行流的行为。当我运行下面的代码时,我希望listOfThings的输出大小与输入大小相同。但事实并非如此,我有时会在输出中丢失项目。这种行为是不一致的。如果我只是在迭代器中迭代,而不是使用parallelStream,那么一切都很好。每次都要计算匹配数 // listRDD.count = 10 JavaRDD test = listRDD.mapPartitions(iterator -> { List listOfThi

我试图理解spark parallelism中Java8并行流的行为。当我运行下面的代码时,我希望
listOfThings
的输出大小与输入大小相同。但事实并非如此,我有时会在输出中丢失项目。这种行为是不一致的。如果我只是在迭代器中迭代,而不是使用
parallelStream
,那么一切都很好。每次都要计算匹配数

// listRDD.count = 10
JavaRDD test = listRDD.mapPartitions(iterator -> {
    List listOfThings = IteratorUtils.toList(iterator);
    return listOfThings.parallelStream.map(
        //some stuff here
    ).collect(Collectors.toList());
});
// test.count = 9
// test.count = 10
// test.count = 8
// test.count = 7
  • 这是一个很好的问题
  • 这里发生的是比赛状态。当您并行化流,然后流将整个列表拆分为几个相等的部分[基于可用线程和列表大小],然后它尝试在每个可用线程上独立运行子部分以执行工作 但是您也在使用ApacheSpark,它以计算速度更快而著名,即通用计算引擎。Spark使用相同的方法[并行化工作]执行操作

    现在在这个场景中,正在发生的事情是Spark已经并行化了整个工作,然后在这个场景中,你再次并行化了工作,因为这个竞态条件开始了,即Spark executor开始处理工作,然后你并行化了工作,然后流处理获得了其他线程,如果线程正在处理流工作在SPARK EXECUTOR完成其工作之前完成工作,然后添加结果,否则SPARK EXECUTOR将继续向MASTER报告结果

  • 这不是一个很好的方法来重新并行的工作,它总是给你的痛苦让火花为你做
  • 希望你明白这里发生了什么


    谢谢投了否决票的人。你能告诉我为什么吗?虽然我同意在Spark内部重新并行工作似乎不是一个好主意,但我认为Akash的答案并不正确。我想我们需要更多的细节来回答这个问题。一个明显的想法是记录
    listOfThings
    的大小,或者只是将其作为
    map
    的一部分添加到输出中。我怀疑在这个阶段事情可能已经破裂了。谢谢你的回复。你能详细说明一下吗?好了,Spark启动单个执行器,所有任务都在JVM中运行。那么,当JVM中仍有线程在并行流中运行时,spark executor如何完成呢?@Falan,因为并行流运行在不同的执行器上,因此spark;s线程不会控制并行流线程。为了让spark线程等待并行流完成它的工作,您必须使用线程连接。@Falan希望您现在了解spark映射中并行流的运行情况。。它在我的本地和我的spark cluster中运行良好。。我如何重现这个问题?