hadoop将MapReduce计算转移到存储有部分数据的各个机器的具体过程

作者: admin 分类: Hadoop 发布时间: 2018-02-27 09:21  阅读: 625 views

首先定义一些术语。MapReduce作业(job)是客户端需要执行的一个工作单元:它包括输入数据、MapReduce程序和配置信息。Hadoop将作业分成若干个小任务(task)来执行,其中包括两类任务:map任务和reduce任务。

有两类节点控制着作业执行过程:一个jobtracker以及一些列tasktracker。jobtracker通过调度tasktracker上运行的任务来协调所有运行在系统上的作业。tasktracker在运行人任务的同时将运行进度报告发送给jobtracker,jobtracker由此记录每项作业任务的整体进度情况。如果其中一个任务失败,jobtracker可以在另外一个tasktracker节点上重新调度该任务。

Hadoop将MapReduce的输入数据划分成等长的小数据块,称为输入分片(input split)或简称“分片”。Hadoop为每个分片构建一个map任务,并由该任务来运行用户自定义的Map函数从而处理分片中的每条记录。

拥有许多分片,意味着处理每个分片所需要的时间少于处理整个输入数据所花的时间。因此,如果我们并行处理每个分片,且每个分片数据比较小,那么整个处理过程将获得更好的负载平衡,因为一台较快的计算机能够处理的数据分片比一台较慢的计算机更多,且成一定的比例。即使使用相同的机器,失败的进程或其他同时运作的作业能够实现满意的负载平衡,并且如果分片被切分得更细,负载平衡的会更高。

另一方面,如果分片切分的太小,那么管理分片的总时间和构建map任务的总时间将决定作业的整个执行时间。对于大多数作业来说,一个合理的分片大小趋向于HDFS的一个快的大小,默认是64MB,不过可以针对集群调整这个默认值(对新建的文件),或对新建的每个文件具体制定。

Hadoop在存储有输入数据(HDFS中的数据)的节点上运行map任务,可以获得最佳性能。这就是所谓的“数据本地化优化(data locality optimization)”,因为它无需使用宝贵的集群宽带资源。但是,有时对于一个map任务的输入来说,存储有某个HDFS数据块备份的三个节点可能正在运行其他map任务,此时作业调度需要在三个备份中的某个数据寻求同个机架中空闲的机器来运行该map任务。仅仅在非常偶然的情况下,会使用其他机架中的机器运行该map任务,这将导致机架与机架之间的网络传输产生效率问题。如下图

本地数据(a),本地机架(b)和跨机架(c)map任务

 

现在可以清楚知道为什么最佳分片的大小应该与块大小相同:因为它是确保可以存储在单个节点上的最大输入块的大小。如果分片跨越两个数据块,那么对于任何一个HDFS节点,基本上都不可能同时存储这两个数据块,因此分片中的部分数据需要通过网络传输到map任务节点。与使用本地数据运行整个map任务相比,这种方法显然效率更低。

map任务将其输出写入本地硬盘,而非HDFS,是因为map的输出是中间结果:该中间结果由reduce任务处理后才产生最终输出结果,而且一旦作业完成,map的输出结果就可以删除。所以,如果把他存储在HDFS中并实现备份,没有必要。如果该节点上运行的map任务将map中间结果传送给reduce任务之前失败,Hadoop将在另一个节点上重新运行这个map任务以再次构建map中间结果。

reduce任务并不具备数据本地化的优势- 单个reduce任务的输入通常来自于所有mapper的输出。排过序的map输出需要通过网络传输发送到运行reduce任务的节点。数据在reduce端合并,然后由用户定义的reduce函数处理。reduce的输出通常存储在HDFS中以实现可靠存储。对于每个reduce输出的HDFS块,第一个副本存储在本地节点上,其他副本存储在其他机架节点中。将reduce的输出写入HDFS确实需要占用网络宽带,但这与正常的HDFS流水线写入的消耗一样。

一个reduce任务的完整数据流如图所示(一个reduce任务的MapReduce数据流)。

虚线框标识节点,虚线箭头表示节点内部的数据传输,而实现箭头表示不同节点之间的数据传输。

 

reduce任务的数量并非由输入数据的大小决定,而是独立指定的。

如果有好多个reduce任务,每个map任务就会针对输出进行分区(partitioin),即为每个reduce任务建一个分区。每个分区有许多键(及其对应的值),但每个键对应的键值对记录都在同一分区中。分区由用户定义的partition函数控制,但通常用默认的partitioner通过哈希函数来区分,很高效。

一般多个reduce任务的数据流如图所示(多个reduce任务的数据流)。

 

 

上图清楚地表明了为什么map任务和reduce任务之间的数据流称之为 shuffle(混洗),因为每个reduce任务的输入都来自许多map任务。shuffle一般比途中所示的更复杂,而且调整混洗参数对作业总执行时间的影响非常大。

最后,当数据处理可以完全并行,即无需混洗时,可能会出现无reduce任务的情况。在这种情况下,唯一的非本地节点数据传输是map任务将结果写入HDFS, 如下图


   原创文章,转载请标明本文链接: hadoop将MapReduce计算转移到存储有部分数据的各个机器的具体过程

如果觉得我的文章对您有用,请随意打赏。您的支持将鼓励我继续创作!

发表评论

电子邮件地址不会被公开。 必填项已用*标注

更多阅读