SparkShuffle 调优
- 程序调优; 首先,尽量减少 shuffle 次数; //两次 shuffle rdd.map().repartition(1000).reduceByKey(+,3000) //一次 shuffle
Rdd.map().repartition(3000).reduceByKey(+) 然后必要时主动
shuffle,通常用于改变并行度,提高后续分布式运行速度;
rdd.repartition(largerNumPartition).map() 最后,使用
treeReduce&treeAggregate 替换 reduce&aggregate。数据量较大
时,reduce&aggregate 一次性聚合,shuffle 量太大,而 treeReduce&treeAggregate
是分批聚合,更为保险。
参数调优;
-
spark.shuffle.file.buffer
:map task 到 buffer 到磁盘 默认值:32K
参数说明:该参数用于设置 shuffle write task 的 BufferedOutputStream 的 buffer
缓冲大小。将数据写到磁盘文件之前,会先写入 buffer 缓冲中,待缓冲写满之后, 才会溢写到磁盘;
调优建议:如果作业可用的内存资源较为充足的话,可以适当增加这个参数 的大小(比如 64k),从而减少 shuffle write
过程中溢写磁盘文件的次数,也就可 以减少磁盘 IO 次数,进而提升性能。在实践中发现,合理调节该参数,性能会 有 1 到 5%的提升。 -
spark.reducer.maxSizeFlight
:reduce task 去磁盘拉取数据 默认值:48m
参数说明:该参数用于设置 shuffle read task 的 buffer 缓冲大小,而这个 buffer
缓冲决定了每次能够拉取多少数据。 调优建议:如果作业可用的内存资源较为充足的话,可以增加这个参数的大 小(比如
96M),从而减少拉取数据的次数,也就可以减少网络传输的次数,进而 提升性能。在实践中发现,合理调节该参数,性能会有 1 到
5%的提升。 -
Spark.shuffle.io.maxRetries
默认值:3 参数说明:shuffle read task 从 shuffle write task 所在节点拉取属于自己的数据
时,如果因为网络异常导致拉取失败,时会自动进行重试的。该参数就代表了可
以重试的最大次数,如果在指定次数内拉取属于还是没有成功,就可能会导致作 业执行失败。 调优建议:对于那些包含了特别耗时的 shuffle
操作的作业,建议增加重试 最大次数(比如 6 次),可以避免由于 JVM 的 full gc 或者网络不稳定等因素导致
的数据拉取失败。在实践中发现,对于超大数据量(数十亿到上百亿)的 shuffle 过程,调节该参数可以大幅度提升稳定性。 -
Spark.shuffle.io.retryWait
默认值:5s 参数说明:shuffle read task 从 shuffle write task 所在节点拉取属于自己的数据
时,如果拉取失败了每次重试拉取数据的等待时间间隔,默认是 5s;
调优建议:建议加大时间间隔时长,比如 60s,以增加 shuffle 操作的稳定性。 -
spark.shuffle.memoryFraction
默认值:0.2 参数说明:该参数代表了 executor 内存中,分配给 shuffle read task 进行聚合
操作的内存比例,默认是 20%; 调优建议:如果内存充足,而且很少使用持久化操作,建议调高和这个比例, 给 shuffle read
的聚合操作更多内存,以避免由于内存不足导致聚合过程中频繁 读写磁盘。在实践中发现,合理调节该参数可以将性能提升 10%。