MapReduce全流程
作者:尹正杰
版权声明:原创作品,谢绝转载!否则将追究法律责任。
一.MapReduce全流程概述
假设有一个文件有2G的文件需要处理,且文件的块大小默认是128MB,接下来我们对MapReduce基于YARN的全流程进行分析.其大致流程如下: 1>.客户端在submit()之前,获取待处理的信息,然后根据参数配置形成一个任务分配的规划并将任务信息提交到YARN;
2>.YARN收到客户端的任务申请会给客户端分配一个任务ID,此过程我们在介绍YARN的工作原理会详细介绍;
3>.客户端根据YARN返回的任务ID里会将只当的文件提交到YARN指定的HDFS路径(比如job.split,wc.jar,job.xml等);
4>.YARN集群根据客户端提供的切片信息计算处MapTask数量(Split数量=MapTask数量);
5>.默认使用TextInputFotmat(这个我在之前介绍过,它的主要功能就是将待处理的文本文件进行一系列的序列化操作,即原始数据变成<K,V>类型)处理后交由Mapper程序;
6>.Mapper程序同固map函数开始逻辑运算,并通过Context.write(k,v)将数据写入outputCollector(对应源码NewOutputCollector类的collector.collect方法);
7>.上一步其实就是将数据写入到一个环形缓冲区,既然是缓冲区那必定有内存限制,默认是100M,当缓存内存使用量超过80%会溢出到磁盘;
8>.数据在溢写磁盘之前,需要在环形缓冲区中进行分区并排序(默认采用快排算法),这样可以保证每个分区的数据是有序的;
9>.将排序后的数据(分区且区内有序)溢出到本地磁盘文件之前,如果你定义了Combiner的话会将任务交给Combiner程序处理后再写入磁盘,注意哈,随着溢出数据的增加,我们会发现每个节点有多个临时溢出数据的小文件;
10>.将溢出的数据归并排序(Merge),最终多溢出个分区文件合并成一个(按照Key的大小)有序的文件(即MapTask的最终输出文件,意味着MapTask任务结束);
11>.如上所述,等待所有的MapTask任务完成后,启动相应数量的ReduceTask,并告知ReduceTask处理数据范围为(数据分区);、
12>.各个MapTask根据得到的ReduceTask处理数据范围(数据分区),将相同的Key发送到同一个ReduceTask,这个过程叫做shuffer;
13>.当ReduceTask本地磁盘接收所有的MapTask发来的数据足够多时,内存不够依旧会溢出到本地磁盘,此时可能会有多个文件需要合并文件,即对每个map来的数据进行归并排序,得到一个数据有序的文件;
14>.将合并后的数据交给Reducer程序处理(一次读取一组数据);
15>.通过GroupingComparator(k,knext)按照相同的Key进行分组;
16>.最终数据默认通过TextOutputFormat将任务的最终计算结果写入到ReduceTask磁盘;
二.MapReduce开发总结
在编写MapReduce程序时,需要考虑如下几个方面:
1>.输入数据接口(InputFormat)
(a)默认使用的实现类时TextInputFormat;
(b)TextInputFormat的功能逻辑是:一次读一行文本,然后将改行的起始偏移量作为key,行内容作为value返回;
(c)KeyValueTextInputFormat没衣阿华那个均为一条记录,被分割分分割为key,value。默认分隔符是tab(" ");
(d)NlineInputFormat按照指定的行数N来划分切片;
(e)CombineTextInputmat可以把多个小文件合并程一个切片处理,提高处理效率;
(f)用户还可以自定义InputFormat;
2>.Mapper逻辑处理接口
用户根据业务需求实现其中三个方法:map(),setup(),cleanup()。
3>.Partition分区
(a)有默认实现HashPartitioner,逻辑是根据key的哈希值和numReduces来返回一个分区号,即"key.hashCode()&Inter.MaxVALUE%numReduces";
(b)如果业务上有特别的需求,可以自定义分区;
4>.Comparable排序
(a)当我们用自定义的对象作为key来输出时,就必须要实现WritableComparable接口,重写其中的compareTo()方法;
(b)部分排序:对最终输出的每一个文件进行内部排序;
(c)全排序:对所有数据进行排序,通常只有一个Reduce;
(d)二次排序:排序的条件有两个;
5>.Combiner合并
Combiner合并可以提高程序执行效率,减少IO传输。但是使用时必须不能影响原有业务处理结果。
6>.Reduce端分组(GroupingCommparator)
在Reduce端对key进行分组。应用于:在接收的key为bean对象时,想让一个或几个字段相同(全部字段比较不相同)的key进入到同一个reduce方法时,可以采用分组排序。
7>.Reducer逻辑处理接口
用户根据业务需求实现其中三个方法:setup(),reduce(),cleanup()。
8>.输出数据接口(OutoutFormat)
(a)默认实现类是TextOutputFormat,功能逻辑是:将每一个KV对,向目标文本文件输出一行;
(b)将SequenceFileOutputFormat输出作为后续MapReduce任务的输入,这便是一种好的输出格式,因为它的格式紧凑,很容易被压缩;
(c)用户还可以自定义OutputFormat;
三.博主推荐阅读
自定义InputFormat代码实现: https://www.cnblogs.com/yinzhengjie2020/p/12521292.html 分区(partitioner): https://www.cnblogs.com/yinzhengjie2020/p/12527426.html 排序(WritableComparable): https://www.cnblogs.com/yinzhengjie2020/p/12528395.html 合并(Combiner): https://www.cnblogs.com/yinzhengjie2020/p/12528612.html Shuffle原理: https://www.cnblogs.com/yinzhengjie2020/p/12535628.html GroupingComparator分组(辅助排序/组内排序): https://www.cnblogs.com/yinzhengjie2020/p/12535193.html 自定义OutputFormat代码实现: https://www.cnblogs.com/yinzhengjie2020/p/12771356.html Reduce Join实战案例: https://www.cnblogs.com/yinzhengjie2020/p/12783256.html Map Join实战案例: https://www.cnblogs.com/yinzhengjie2020/p/12811796.html 计数器应用-数据清洗案例: https://www.cnblogs.com/yinzhengjie2020/p/12815355.html