shuffle:系统执行排序,将map输出作为输入传给reduce的过程称为shuffle。mapreduce确保每个reduce的输入都是按键排序的。
map端
每个map都有一个缓冲区用于任务输出,当到达阀值(默认80%)会写到溢出文件里,最终写到一个磁盘里,在写磁盘前会根据最终的reduce将数据分区排序,排序后运行combiner函数使写到磁盘的数据更紧凑从而减少写的数据量和传输到reduce的数据量。
还可以对map的输出进行压缩,执行参数mapreduce.map.output.compress即可,这样可以使磁盘写入速度变快,节省磁盘空间。
sethive.exec.compress.intermediate=true; 开启hive中间传输数据压缩功能
reducer通过HTTP得到输出文件的分区
reduce端
map的输出文件位于tasktracker本地磁盘。
首先使reduce的复制阶段,在每个任务完成时,reduce任务就开始复制map的输出。如果map的输出很小则输出到reduce的内存,否则还是会输出到磁盘上。随着后台文件增多,后台线程会合并为更大的,排好序的文件,为后续reduce的合并节省时间。
然后是排序阶段。这个阶段合并map的文件,合并的文件数目由参数mapreduce.task.io.sort.factor执行,默认为10.
最后是reduce阶段,将所有的文件合并,之前的合并只是为了满足这个阶段的合并系数。然后输出到文件系统
set mapreduce.output.fileoutputformat.compress=true; 开启mapreduce最终输出数据压缩
配置调优
总的原则是shuffle过程由足够的内存空间。
map端
可以通过避免多次溢出磁盘来获取最佳性能,所以可以优先考虑设置参数mapreduce.task.io.sort.mb,这个参数是排序map所用的缓冲区的大小,单位是m
reduce端
如果reduce函数内存要求不大,主要设置
mapreduce.reduce.merge.inmem.threshold = 0
mapreduce.reduce.input.buffer.percent 小于1.0 为了减少访问磁盘次数
网友评论