文档章节

Shuffle的洗牌过程

HIVE
 HIVE
发布于 2016/07/01 22:52
字数 1607
阅读 305
收藏 1

Shuffle的正常意思是洗牌或弄乱

 

 

 

 

 

Shuffle描述着数据从map task输出到reduce task输入的这段过程。.

 

大部分map task与reduce task的执行是在不同的节点上。当然很多情况下Reduce执行时需要跨节点去拉取其它节点上的map task结果。

 

我们对Shuffle过程的期望可以有:

完整地从map task端拉取数据到reduce 端。在跨节点拉取数据时,尽可能减少对带宽的不必要消耗。减少磁盘IO对task执行的影响。

 

 

 

Shuffle解释

每个map task都有一个内存缓冲区,存储着map的输出结果,当缓冲区快满的时候需要将缓冲区的数据以一个临时文件的方式存放到磁盘,当整个map task结束后再对磁盘中这个map task产生的所有临时文件做合并,生成最终的正式输出文件,然后等待reduce task来拉数据。

 

1、在map task执行时,它的输入数据来源于HDFS的block,当然在MapReduce概念中,map task只读取split。Split与block的对应关系可能是多对一,默认是一对一。

 

2、在经过mapper的运行后,我们得知mapper的输出是这样一个k/v键值

。在这只做统计,reduce才做合并。

 

3.Partitioner接口,它的作用就是根据key或value及reduce的数量来决定当前的这对输出数据最终应该交由哪个reduce task处理。默认对key hash后再以reduce task数量取模。默认的取模方式只是为了平均reduce的处理能力,如果用户自己对Partitioner有需求,可以订制并设置到job.set(..)

 

4(Memory Buffer)接下来我们将数据写入到内存缓冲区中,缓冲区的作用是批量收集map结果,减少磁盘IO的影响。我们的key/value对以及Partition的结果都会被写入缓冲区。当然写入之前,key与value值都会被序列化成字节数组。

 

5内存缓冲区是有大小限制的,默认是100MB。map task 的输出结果大于这个内存缓冲区的阀值是(buffer size * spill percent = 100MB * 0.8 = 80MB

溢写线程启动,把这80M在缓冲区的数据写入到磁盘中,Map task向剩下20MB在内存中,互补影响。这个从内存往磁盘写数据的过程被称为Spill

 

 

当溢写线程启动后,需要对这80MB空间内的key做排序(Sort)。排序是MapReduce模型默认的行为,这里的排序也是对序列化的字节做的排序。

 

图上也可以看到写到磁盘中的溢写文件是对不同的reduce端的数值做过合并。所以溢写过程一个很重要的细节在于,如果有很多个key/value 对需要发送到某个reduce端去,那么需要将这些key/value值拼接到一块,减少与partition相关的索引记录。

 

6.如果client设置过Combiner,那么现在就是使用Combiner的时候了。将有相同key的key/value对的value加起来,减少溢 写到磁盘的数据量。Combiner会优化MapReduce的中间结果,所以它在整个模型中会多次使用。那哪些场景才能使用Combiner呢?从这里 分析,Combiner的输出是Reducer的输入,Combiner绝不能改变最终的计算结果。所以从我的想法来看,Combiner只应该用于那种 Reduce的输入key/value与输出key/value类型完全一致,且不影响最终结果的场景。比如累加,最大值等。Combiner的使用一定 得慎重,如果用好,它对job执行效率有帮助,反之会影响reduce的最终结果。

 

7.每次溢写会在磁盘上产生一个溢写文件,Map 输出结果很大时,会有多次这样的溢写文件到磁盘上,当 Map task 结束完成时,内存缓冲区的数据同样也会溢写到磁盘上,结果磁盘会有一个或多个溢出的文件,同时合并溢出的文件。(如果map输出的结果很少,map完成时,溢出的文件只有一个)合并这个过程就叫做Merge{墨迹}

 

merge是将多个溢写文件合并到一个文件,所以可能也有相同的key存在,在这个过程中如果client设置过Combiner,也会使用Combiner来合并相同的key。

 

此时,map端的工作都已结束,最终生成的文件也存放在Task Tracker本地目录内,每个reduce task 不断的通过RPC 从JOBTracker哪里获取 map task 是否完成,如果reduce task 得到通知,通知到某台Task Tracker 上的map task执行完成,shuffle的reducece开始拉去map Task完成的数据

 

 

Reducer真正运行之前,所有的时间都是在拉取数据,做merge,且不断重复地在做。如前面的方式一样,分段地描述reduce 端的Shuffle细节

 

1.copy 过程,就是拉取数据。Reduce进程启动一些copy线程,通过Http方式请求 map task 所在的TaskTracker获取map task的输出文件。应为map task 已经结束,这文件就归TaskTracker管理了,管理在本地磁盘中。

 

2.copy过来的数据会先储存在内存缓冲区中(Memory Buffer),这里的缓冲区要比map端的更加灵活,它基于JVM的heap size 的设置,因为shuffle阶段rduce不运行,所以把大部分的内存给shuffle来用,

这里和map中内存溢出一样,当内存中的数据达到一定的阀值,就会启动内存到磁盘的溢出....合并Merge   。这个过程我们设置Combiner,也会启用的,然后在磁盘中生成很多一些文件。值到map端没有数据才结束。然后启动第三种磁盘到磁盘的merge方式生成最终的那个文件。

 

3.Reduce的输入文件,不断的合并后(merge),最后会生成一个“最终文件”,这个文件可能存在磁盘上也能在内存中(内存需要设置并且优化),默认在磁盘中,当Reducer的输入文件已定,整个Shuffle才最终结束。然后就是Reducer执行,把结果放到HDFS上。

© 著作权归作者所有

下一篇: hbase优化配置
HIVE
粉丝 5
博文 9
码字总数 18467
作品 0
昌平
架构师
私信 提问
打造属于自己的underscore系列(六)- 洗牌算法

javascript如何将一个无序的数组变成一个有序的数组,我们有很多的排序算法可以实现,例如冒泡算法,快速排序,插入排序等。然而我们是否想过,如何将一个有序的数组乱序输出呢?本文将从经典...

不做祖国的韭菜
02/17
0
0
map-reduce 、map、reduce

map-reduce 过程 中间绿线区域就是shuffle(“洗牌”)过程:map之后,reduce之前的过程。 可以这样理解:一个map 产生的数据,结果通过hash过程分区却分配给了不同的reduce任务,就相当于对...

八戒_o
2015/11/09
162
0
perfect shuffle 算法的一个线性复杂度实现

今天又发现一个关于完美洗牌的算法。这个比较简单一些,由 microsoft的Peiyush Jain提出。 原论文: A Simple In-Place Algorithm for In-Shuffle. Peiyush Jain, Microsoft Corporation. J...

吟啸_徐行
2014/03/20
216
2
[CareerCup] 18.2 Shuffle Cards 洗牌

18.2 Write a method to shuffle a deck of cards. It must be a perfect shuffle—in other words, each of the 52! permutations of the deck has to be equally likely. Assume that you ......

机器的心脏
2017/12/14
0
0
[LeetCode] Shuffle an Array 数组洗牌

Shuffle a set of numbers without duplicates. Example: // Init an array with set 1, 2, and 3.int[] nums = {1,2,3};Solution solution = new Solution(nums);// Shuffle the array [1,2......

机器的心脏
2017/12/12
0
0

没有更多内容

加载失败,请刷新页面

加载更多

高速PCB设计软件allegro中与网络有关的约束规则设置

在allegro pcb的设计过程中,设计约束规则包括时序规则、间距规则、信号完整性规则以及物理规则等,本期主要详细讲解与物理、间距与电气约束中的线宽、线间距物理规则的设置。 一、线宽设置 ...

demyar
19分钟前
2
0
Linux 启动停止SpringBoot jar 程序部署Shell 脚本

#!/bin/bash #这里可替换为你自己的执行程序,其他代码无需更改 APP_NAME=algorithm.jar #使用说明,用来提示输入参数 usage() { echo "Usage: sh 执行脚本.sh [start|stop|restart|status]...

草庐过客
21分钟前
3
0
mysql-connector-java驱动升级到8.0后数据库保存时间出现时差

1.问题:在一个新项目中用到了新版的mysql jdbc 驱动后,发现保存到数据库的时间出现了时差 <dependency> <groupId>mysql</groupId> <artifactId>mysql-connector-java</artifactId>......

ValSong
22分钟前
3
0
好程序员大数据教程Scala系列之隐式转换和隐式参数

5.1. 概念 隐式转换和隐式参数是Scala中两个非常强大的功能,利用隐式转换和隐式参数,你可以提供优雅的类库,对类库的使用者隐匿掉那些枯燥乏味的细节。 5.2. 作用 隐式的对类的方法进行增强...

好程序员官网
26分钟前
3
0
多线程必备

初次接触线程,可能有很多初学者搞不明白,始终云里雾里,那么本篇文章直接带大家介绍多线程必须知道的几个点 接下来没有多余,直接上干货 1. 进程和线程的区别是什么? 进程是执行着的应用程序,...

理性思考
29分钟前
4
0

没有更多内容

加载失败,请刷新页面

加载更多

返回顶部
顶部