下面是一篇与你 Spark 系列风格统一、可直接发布的第 七十三篇教程文章 👇
大数据 Spark(七十三):Transformation 转换算子 glom 和 foldByKey 使用案例
在 Spark 的 Transformation 转换算子中,有些算子不常用,但一旦用到就非常关键。
本篇我们重点讲解两个非常典型、但使用场景完全不同的算子:
glom —— 面向分区的数据观察算子
foldByKey —— 带初始值的 Key 聚合算子
理解它们,有助于你真正理解 Spark 的分区机制和 Key 聚合过程。
一、glom 算子详解
1️⃣ glom 是什么?
def glom(): RDD[Array[T]]
glom 的作用是:
将每个分区中的所有元素,转换成一个数组
也就是说:
- 一个分区 → 一个
Array - 元素不变,结构改变
2️⃣ glom 的核心特点
| 特点 | 说明 |
|---|---|
| 作用对象 | 分区 |
| 是否触发 Shuffle | ❌ 不会 |
| 是否改变分区数 | ❌ 不会 |
| 常见用途 | 查看分区数据、分区内统计 |
3️⃣ 使用案例:查看每个分区的数据
val conf = new SparkConf().setMaster("local[*]").setAppName("GlomDemo")
val sc = new SparkContext(conf)
val rdd = sc.parallelize(1 to 10, 3)
val result = rdd.glom()
result.collect().foreach(arr => {
println(arr.mkString(","))
})
sc.stop()
示例输出:
1,2,3
4,5,6
7,8,9,10
👉 非常适合:
- 调试分区是否均匀
- 验证 repartition / coalesce 效果
4️⃣ 使用案例:计算每个分区的最大值
val rdd = sc.parallelize(1 to 10, 3)
val maxPerPartition = rdd.glom().map(arr => arr.max)
maxPerPartition.collect().foreach(println)
⚠️ glom 使用注意事项
- 会把分区数据一次性加载到内存
- 不适合数据量特别大的分区
- 更偏向 调试 / 分析用途
二、foldByKey 算子详解
1️⃣ foldByKey 是什么?
def foldByKey(zeroValue: V)(func: (V, V) => V): RDD[(K, V)]
foldByKey 是一个 Key-Value 聚合算子,可以看作:
带初始值的 reduceByKey
2️⃣ foldByKey 与 reduceByKey 的区别
| 算子 | 是否有初始值 | 聚合逻辑 |
|---|---|---|
| reduceByKey | ❌ | 分区内 = 分区间 |
| foldByKey | ✅ | 分区内 = 分区间 |
⚠️ 注意:foldByKey 分区内和分区间使用的是同一个函数。
3️⃣ 使用案例:按 key 求和(初始值 = 0)
val conf = new SparkConf().setMaster("local[*]").setAppName("FoldByKeyDemo")
val sc = new SparkContext(conf)
val rdd = sc.parallelize(
List(("a", 1), ("a", 2), ("b", 3), ("b", 4)), 2
)
val result = rdd.foldByKey(0)(_ + _)
result.collect().foreach(println)
sc.stop()
输出结果:
(a,3)
(b,7)
4️⃣ 使用案例:按 key 求最大值(初始值 = Int.MinValue)
val rdd = sc.parallelize(
List(("a", 3), ("a", 1), ("b", 5), ("b", 2)), 2
)
val result = rdd.foldByKey(Int.MinValue)(math.max)
result.collect().foreach(println)
⚠️ foldByKey 初始值的重要性
zeroValue每个分区都会使用一次- 选错初始值会导致结果错误
❌ 错误示例(最大值用 0):
foldByKey(0)(math.max)
三、glom + foldByKey 综合理解
| 算子 | 核心关注点 |
|---|---|
| glom | 分区内的数据结构 |
| foldByKey | Key 的聚合规则 |
👉 一个偏向 分区视角
👉 一个偏向 Key 聚合视角
四、使用建议与最佳实践
✅ 什么时候用 glom?
- 调试分区数据
- 查看分区是否倾斜
- 小数据场景下的分区统计
✅ 什么时候用 foldByKey?
- 需要初始值的 Key 聚合
- 聚合逻辑简单统一
- 不想写 aggregateByKey / combineByKey
五、总结
- glom:
👉 看清 Spark 的“分区长什么样” - foldByKey:
👉 带初始值的 reduceByKey
一句话记忆
glom 看分区,foldByKey 聚合 Key。
发表回复