Hadoop中split数量和reader读取原则

画一个简单的hadoop执行图

这里我以单词计数为例,在WCapp(在上篇博文《split数量计算法则》有源码)中设置最小切片数值和最大切片数值,把最大切片数值设置成13,即13个字节

要计数的数据

这里有个问题我们把切片值的设的很小,第一个切片读到的内容:hello world t,那么一个切片装不了一行,数据被切断,那么reader是怎么读的呢?

我们这里还是在jobsubmitter类中的writeSplits中打断点Debug运行程序

step over 到  maps = this.writeNewSplits(job, jobSubmitDir);这一行,然后step into进入

再进入到input.getSplits(job)中

我们可以看到minSize=1,maxSize = 13,这是我们刚才设置最大切块大小的值。(至于这些方法怎么得到这些值的在上一篇文章有讲过)

下面就是一大堆源码,判断是否能切成split(一些压缩是不能切),这些就不说了,有兴趣的自己试验研究。

直接在方法底打断点

可以看到切片数量有四个,我们有三行数据,每行数据量都大于切片值,有四个切片也说的通。在确定每个切片的内容

可以看见有0~3共四个切片,第一个切片行偏移量为0,有13个字节,其他的也以此类推,只有最后一个切片只有10个字节的数据。

一个切片对应一个map任务,那么第一个切片他的map任务切到数据应该是 hello world t

那么我们直接就在自己写的WCmapper中打一个断点,程序运行到这里查看value中的值是否是hello world t

我们可以看到读到值是完整的一行,而不是hello world t

这才合理嘛。如何是按切片值来读,那么很大可以读取到不完整的数据,我们计算的结果也会是错误的。

这里有个很重要的类Recordreader,也就是最上面图上,inputformat到map中间有一个reader,你切片可以这样定义,但是reader要去读数据,他会首先判断读取的位置是不是行首,若是,则会一直读到回车换行;若不是行首,它会从下一行开始读。这就是为什么我们第二个切片内容会是一个完整的行内容,而不是从第一行的 om 开始读。

所以我们虽然有四个切片,但是我们只有前三个split有数据,最后一个split是空的,因为我们只有三行数据,依照reader的读取数据法则,到最后一个split的时候我们已近没有数据可读了。

这里我们可能会问,split和reader这到底听谁的?或者他们俩的功能感觉差不多?

  假设split的大小是128M,我们读了n行数据,在第n行读了一半,如果不读剩下的,会丢数据,这里可能会说,下一个切片把数据读走再分析,但是在并发情况下,切片很大可能在不同节点上运行的,怎么把这两个数据对接在一起再分析。所以这时候就需要reader了,就算我们split值满了,我们还是要把这行读完。(reader是一行一行的把数据发给mapper的)

切片是定义大方向的,而这个reader是处理细节,让你不丢失数据,或者数据不错乱。

  

原文地址:https://www.cnblogs.com/qincan4Q/p/9807877.html

时间: 2024-10-05 05:01:26

Hadoop中split数量和reader读取原则的相关文章

Hadoop中maptask数量的决定因素

刚开始接触hadoop平台的时候 部分初学者对于mapreduce中的maptask的数量是怎么确定的 可能有点迷惑,如果看了jobclient里面的maptask初始化的那段源码,那么就比较清楚了,MapTask的数量是由InputFormat来指定的,InputFormat生成多少个InputSpilt就会有多少个task. 因此,如果剩余Map slot的数量大于InputSpilt的数量,那么就启动的Map数量就是InputSplit的数量. 如果剩余Map slot的数量小于Input

深度分析如何在Hadoop中控制Map的数量

深度分析如何在Hadoop中控制Map的数量 [email protected] 很多文档中描述,Mapper的数量在默认情况下不可直接控制干预,因为Mapper的数量由输入的大小和个数决定.在默认情况下,最终input 占据了多少block,就应该启动多少个Mapper.如果输入的文件数量巨大,但是每个文件的size都小于HDFS的blockSize,那么会造成 启动的Mapper等于文件的数量(即每个文件都占据了一个block),那么很可能造成启动的Mapper数量超出限制而导致崩溃.这些逻

在Publisher DB中查看未被Log Reader读取的Transaction 和 Commands

在Publisher DB中,如果 sys.objects 的 is_published =1,或 sys.tables 的 is_published=1 或 is_replicated=1,表示该Table是Publication的Article,对这些object的更新,产生的事务会被标记为Replicated,需要被Log Reader读取到Distribution中.在同一时间,只有一个Connection拥有读取Transaction Log的权限.调用 sp_replshowcmds

Hadoop中HDFS读取和写入的工作原理

介绍 HDFS和HBase是Hadoop中两种主要的存储文件系统,两者适用的场景不同,HDFS适用于大文件存储,HBASE适用于大量小文件存储. 本文主要讲解HDFS文件系统中客户端是如何从Hadoop集群中读取和写入数据的,也可以说是block策略. 正文 一 写入数据 当没有配置机架信息时,所有的机器hadoop都默认在同一个默认的机架下,名为"/default-rack",这种情况下,任何一台 datanode机器,不管物理上是否属于同一个机架,都会被认为是在同一个机架下,此时,

Hadoop介绍-4.Hadoop中NameNode、DataNode、Secondary、NameNode、JobTracker TaskTracker

Hadoop是一个能够对大量数据进行分布式处理的软体框架,实现了Google的MapReduce编程模型和框架,能够把应用程式分割成许多的 小的工作单元,并把这些单元放到任何集群节点上执行.在MapReduce中,一个准备提交执行的应用程式称为「作业(job)」,而从一个作业划分出 得.运行于各个计算节点的工作单元称为「任务(task)」.此外,Hadoop提供的分布式文件系统(HDFS)主要负责各个节点的数据存储,并实现了 高吞吐率的数据读写. 在分布式存储和分布式计算方面,Hadoop都是用

在Hadoop中重写FileInputFormat类以处理二进制格式存储的整数

最近开始使用MapReduce,发现网上大部分例子都是对文本数据进行处理的,也就是说在读取输入数据时直接使用默认的TextInputFormat进行处理即可.对于文本数据处理,这个类还是能满足一部分应用场景.但是如果要处理以二进制形式结构化记录存储的文件时,这些类就不再适合了. 本文以一个简单的应用场景为例:对按照二进制格式存储的整数做频数统计.当然,也可以在此基础上实现排序之类的其他应用.实现该应用的主要难点就是如何处理输入数据.参考<权威指南·第三版>得知需要继承FileInputForm

结合手机上网流量业务来说明Hadoop中的自定义数据类型(序列化、反序列化机制)

大家都知道,Hadoop中为Key的数据类型必须实现WritableComparable接口,而Value的数据类型只需要实现Writable接口即可:能做Key的一定可以做Value,能做Value的未必能做Key.但是具体应该怎么应用呢?--本篇文章将结合手机上网流量业务进行分析. 先介绍一下业务场景:统计每个用户的上行流量和,下行流量和,以及总流量和. 本次描述所用数据: 日志格式描述: 日志flowdata.txt中的具体数据: 接下来贴出详细代码,代码中含有详细注释,从代码中可以看出,

浅析 Hadoop 中的数据倾斜

转自:http://my.oschina.net/leejun2005/blog/100922 最近几次被问到关于数据倾斜的问题,这里找了些资料也结合一些自己的理解. 在并行计算中我们总希望分配的每一个task 都能以差不多的粒度来切分并且完成时间相差不大,但是集群中可能硬件不同,应用的类型不同和切分的数据大小不一致总会导致有部分任务极大的拖慢了整个任务的完成时间,硬件不同就不说了,应用的类型不同其中就比如page rank 或者data mining 里面一些计算,它的每条记录消耗的成本不太一

hadoop中的序列化与Writable类

本文地址:http://www.cnblogs.com/archimedes/p/hadoop-writable-class.html,转载请注明源地址. hadoop中自带的org.apache.hadoop.io包中有广泛的writable类可供选择,它们形成下图所示的层次结构: java基本类型的Writable封装器 Writable类对java基本类型提供封装,short和char除外,所有的封装包含get()和set()两个方法用于读取或设置封装的值 java基本类型的Writabl