尽早停止Spark中的reduce操作

时间:2018-11-06 14:53:38

标签: scala apache-spark break

有没有办法在Spark中“中断” reduce操作?

假设我要这样做:

var result: Int = 0
while (iterator.hasNext()) {
    if (/*Some condition on result*/) {
        result = someFunction(result, iterator.next())
    } else {
        break
    }
}

在Spark中执行此操作的方法是reduce的RDD(包含迭代器返回的内容):

rdd.reduce((result, next) =>
    if (/*Some condition on result*/) someFunction(result, next)
    else result
)

但是如果计算条件很昂贵怎么办?我可以这样做:

//result is now of type (Int, Boolean) and the initial Boolean is true
rdd.reduce((result, next) =>
    if (result._2 && /*Some condition on result*/) (someFunction(result._1, next._1), true)
    else (result._1, false)
)

有没有更清洁的方法?

1 个答案:

答案 0 :(得分:1)

不幸的是,您想要执行的操作不一定适合spark的计算模型。由于数据是跨分区划分的,因此不一定有明确定义的顺序。如果您不使用spark,则适当的函数调用应为takeWhile

val data: List[DType] = ...
...
data.takeWhile(condition).map(someFunction)

您几乎可以通过mapPartitions获得此功能。这会将功能应用于每个分区上的迭代器。

val data: RDD[DType] = ...
...
data.mapPartitions(partitionData: Iterator[DType] => partitionData.takeWhile(condition).map(someFunction))