一、序引
当以分布式方式处理数据时,常常需要执行map与reduce转换。由于巨量数据必须从一个节点传输到另外的节点,给集群中的cpu、磁盘、内存造成沉重的负载压力,同时也会给网络带宽带来压力。所以,reduce阶段进行的shuffle过程,往往是性能的瓶颈所在。
shuffle过程涉及数据排序、重分区、网络传输时的序列化与反序列化,为了减少I/O带宽及磁盘I/O操作,还要对数据进行压缩。故而,shuffle的性能将直接spark的整体运算性能。
因为shuffle文件数(M(Map数) * R(Reduce数))将会非常大。故而,这是性能损失的关键所在。折衷方案:压缩输出文件。spark默认的是Snappy,但也支持选择lz4、lzf。
reduce阶段,内存问题异常突出。对于一个reducer而言,被shuffle的所有数据都必须放到内存中。若内存不够,则会因内存溢处而导致job失败。同时,这也是为何reducer数量如此重要的原因。reducer增加时,理应及时减少每个reducer对应的数据量。
Hadoop与Spark的对比:hadoop中,map与reduce阶段存在交叠,mapper把输出数据推送到reducer;spark中,只有map阶段结束,reduce阶段才启动工作,reducer将拉取shuffle后的数据。
在Spark中,引入了shuffle file consolidation机制,尽量输出少一点但大一些的文件。map阶段为每个分区输出一个shuffle文件。shuffle文件数是每个核的reducer数,而不是每个mapper的reducer数。原有运行在相同CPU核上的map任务都将输出相同的shuffle文件,每个reducer都有一个文件。要启用shuffle文件合并,必须把spark.shuffle.consolidateFile=true。
二、Shuffle与数据分区
join、reduceByKey、groupByKey、cogroup等转换(transformation)操作需要在集群中shuffle数据。这些操作可能需要对整个数据集进行shuffle、排序及重新分区,十分消耗性
Spark——性能调优——Shuffle
最新推荐文章于 2025-06-22 16:48:10 发布