总结图
阶段
- Copy阶段
- Sort阶段
- Reduce阶段
Copy阶段
ReduceTask 从各个 MapTask 上远程拷贝一片数据,并针对某一片数据,如果其大小超过一定阈值,则写到磁盘上,否则直接放到内存中。
Sort阶段
在远程拷贝数据的同时,ReduceTask 启动了两个后台线程对内存和磁盘上的文件进行合并,以防止内存使用过多或磁盘上文件过多。
按照 MapReduce 语义,用户编写 reduce()函数输入数据是按 key 进行聚集的一组数据。为了将 key 相同的数据聚在一起,Hadoop 采用了基于排序的策略。
由于各个 MapTask 已经实现对自己的处理结果进行了局部排序,因此,ReduceTask 只需对所有数据进行一次归并排序即可。
Reduce阶段
reduce()函数将计算结果写到 HDFS 上。
ReduceTask 并行度决定机制
设置
ReduceTask 的并行度同样影响整个 Job 的执行并发度和执行效率,但与 MapTask 的并
发数由切片数决定不同,ReduceTask 数量的决定是可以直接手动设置:
// 默认值是 1,手动设置为 4
job.setNumReduceTasks(4);
注意事项
- ReduceTask=0,表示没有Reduce阶段,输出文件个数和Map个数一致。
- ReduceTask默认值就是1,所以输出文件个数为一个。
- 如果数据分布不均匀,就有可能在Reduce阶段产生数据倾斜
- ReduceTask数量并不是任意设置,还要考虑业务逻辑需求,有些情况下,需要计算全
局汇总结果,就只能有1个ReduceTask。 - 具体多少个ReduceTask,需要根据集群性能而定。
- 如果分区数不是1,但是ReduceTask为1,是否执行分区过程。答案是:**不执行分区过程。**因为在MapTask的源码中,执行分区的前提是先判断ReduceNum个数是否大于1。不大于1,肯定不执行。