为什么 Spark 中聚集和折叠两个不同的 API?

2023-12-31

当使用Scala标准库时,我可以这样做:

scala> val scalaList = List(1,2,3)
scalaList: List[Int] = List(1, 2, 3)

scala> scalaList.foldLeft(0)((acc,n)=>acc+n)
res0: Int = 6

从多个 Int 中生成一个 Int。

我可以做这样的事情:

scala> scalaList.foldLeft("")((acc,n)=>acc+n.toString)
res1: String = 123

从许多 Int 中生成一个 String。

因此,foldLeft 可以是同构的,也可以是异构的,无论我们想要哪一种,它都在一个 API 中。

在 Spark 中,如果我想要从多个 Int 中选择一个 Int,我可以这样做:

scala> val rdd = sc.parallelize(List(1,2,3))
rdd: org.apache.spark.rdd.RDD[Int] = ParallelCollectionRDD[1] at parallelize at <console>:12
scala> rdd.fold(0)((acc,n)=>acc+n)
res1: Int = 6

Fold API 与 FoldLeft 类似,但它只是同构的,RDD[Int] 只能产生带有 Fold 的 Int。

Spark 中也有一个聚合 API:

scala> rdd.aggregate("")((acc,n)=>acc+n.toString, (s1,s2)=>s1+s2)
res11: String = 132

它是异构的,一个 RDD[Int] 现在可以生成一个 String。

那么,为什么折叠和聚合在 Spark 中作为两个不同的 API 实现呢?

为什么它们不像 FoldLeft 那样设计,既可以是同质的,也可以是异质的?

(我对 Spark 很陌生,如果这是一个愚蠢的问题,请原谅。)


fold可以更有效地实现,因为它不依赖于固定的评估顺序。这样每个集群节点就可以fold并行地拥有自己的块,然后是一个小的整体fold在最后。而与foldLeft每个元素都必须按顺序折叠,不能并行执行任何操作。

(为了方便起见,为常见情况提供一个更简单的 API 也很好。标准库有reducefoldLeft为此原因)

本文内容由网友自发贡献,版权归原作者所有,本站不承担相应法律责任。如您发现有涉嫌抄袭侵权的内容,请联系:hwhale#tublm.com(使用前将#替换为@)

为什么 Spark 中聚集和折叠两个不同的 API? 的相关文章

随机推荐