zoukankan      html  css  js  c++  java
  • 周总结

    简单描述Shuffle过程环形缓冲区的作用?

    key,value从map()方法输出,被outputcollector收集通过getpartitioner()方法获取分区号,在进入环形缓冲区。默认情况下,环形缓冲区大小值为100MB。当map输入的数据进入环形缓冲区的量达到80MB以上时,那么开始执行溢写过程,溢写过程中如果有其他数据进入,那么由剩余的百分之20反向写入。溢写过程会根据key,value先进行分区,后进行排序,最终maptask溢写文件经过归并排序后落入本地磁盘,reduceTask将多个mapTask下相同分区的数据copy到不同的reduceTask中进行归并排序后一次读取一组数据给reduce()函数。  

    简述Hdfs的默认副本策略?这样做有什么好处?

    1)第一个副本在客户端所处的节点上。如果客户端在集群外(意思就是执行上传的服务器不属于集群的节点),则随机再机架上选一个; (2)第二个副本和第一个副本位于相同机架随机节点上; (3)第三个副本位于不同机架,随机节点。 优点:该策略减少了机架间的写流量,通常可以提高写性能。机架故障的机会远小于节点故障的机会。所以此策略不会影响数据的可靠性和可用性保证。

    简单描述你对Hadoop集群SafeMode模式的理解?

    集群处于安全模式,不能执行重要操作(写操作),集群属于只读状态。但是严格来说,只是保证HDFS元数据信息的访问,而不保证文件的访问。集群启动完成后,自动退出安全模式, 如果集群处于安全模式,想要完成写操作,需要离开安全模式。 (1)bin/hdfs dfsadmin -safemode get (功能描述:查看安全模式状态) (2)bin/hdfs dfsadmin -safemode enter (功能描述:进入安全模式状态) (3)bin/hdfs dfsadmin -safemode leave (功能描述:离开安全模式状态) (4)bin/hdfs dfsadmin -safemode wait (功能描述:等待安全模式状态)。 对于全新创建的HDFS集群,NameNode启动后不会进入安全模式,因为没有Block信息。

    用一句话总结Combiner的作用和意义,使用它有什么前提?

    Combiner的意义就是对每一个MapTask的输出进行局部汇总,以减小网络传输量。

    简述HDFS的文件上传流程?

    1)客户端通过Distributed FileSystem模块向NameNode请求上传文件,NameNode检查目标文件是否已存在,父目录是否存在。 2)NameNode返回是否可以上传。 3)客户端请求第一个 Block上传到哪几个DataNode服务器上。 4)NameNode返回3个DataNode节点,分别为dn1、dn2、dn3。 5)客户端通过FSDataOutputStream模块请求dn1上传数据,dn1收到请求会继续调用dn2,然后dn2调用dn3,将这个通信管道建立完成。 6)dn1、dn2、dn3逐级应答客户端。 7)客户端开始往dn1上传第一个Block(先从磁盘读取数据放到一个本地内存缓存),以Packet为单位,dn1收到一个Packet就会传给dn2,dn2传给dn3;dn1每传一个packet会放入一个应答队列等待应答。 8)当一个Block传输完成之后,客户端再次请求NameNode上传第二个Block的服务器。

    ReduceTask是负责从MapTask上远程读取输入数据后对数据排序,将数据分组传递给用户编写的reduce进行处理

    MapReduce是一个分布式的运算程序编程框架,适合处理大量的离线数据,有良好的扩展性和高容错性

    hdfs是分布式的海量文件存储系统

    web页面访问http://192.168.153.88:50070可以查看hadoop的datanode存活和数据存储的URL地址

    Namenode 全权管理数据块的复制,它周期性地从集群中的每个Datanode接收心跳信号和块状态报告(Blockreport),接收到心跳信号意味着该Datanode节点工作正常

    ResourceManager负责对 NodeManager 资源进行统一管理和调度

    Hadoop1.x和Hadoop2.x区别之一,后则将mapreduce中的资源调度模块拆分为yarn

    下列哪些是对reduceTask阶段任务正确理解:

    对多个mapTask任务输出key,value,按照不同的分区通过网络copy到不同的reduceTask节点处理

    对多个mapTask任务的输出进行合并、排序。再reduce函数中实现自己的逻辑,对输入的key、value处理,转换成新的key、value输出。

    outputformat把reducer输出的key,value保存到文件中

    执行一个job, 如果这个job的输出路径已经存在,那么程序会:

    抛出一个异常,然后退出程序的执行

     会抛出文件路径已存在的异常

    mapreduce数据类型理解正确:

     数据类型都实现Writable接口

    hadoop的序列化中数据可以被序列化进行网络传输和文件存储

    下面对Combiner描述正确的是:

     合理利用Combiner可以提高程序执行效率

     Combiner的作用可以减少对本地磁盘的访问次数。

     Combiner过程设置则执行,否则不执行,默认过程中没有执行Combiner

    Container封装节点上多维度资源包括:

     内存  CPU  磁盘   网络

    ApplicationMaster描述正确的是:

     负责协调来自ResourceManager分配的资源

     通过NodeManager监视任务的执行和资源使用

    fsimage和edits描述正确的是:

    FsImage文件:HDFS文件系统元数据的一个永久性的检查点,其中包含HDFS文件系统的所有目录和文件inode的序列化信息。

    Edits文件:存放HDFS文件系统的所有更新操作的路径,文件系统客户端执行的所有写操作首先会被记录到Edits文件中。

    SecondaryNode实时的辅助备份fsimage和edits,辅助NameNode,协助其完成元数据和编辑文件的合并工作

    关于 SecondaryNameNode :

    它是辅助NameNode ,它的目的是帮助 NameNode 合并编辑日志,减少 NameNode 启动时间和压力,提高NameNode的整体性能

    元数据中包含两个文件是:

    fsimage和edits

    1.mapreduce定义和优缺点?

    MapReduce定义:MapReduce是一个分布式运算的编程框架,使用户开发“基于hadoop的数据分析应用”的核心框架。

    优点:

    1,MapReduce易于编程

    它简单的实现一些接口,就可以完成一个分布式程序,这个分布式程序可以分布到大量廉价的pc机上运行。也就是说写一个分布式程序,跟写一个简单的串行程序是一模一样的。就是因为这个特点使得MapReduce编程变得非常流行。

    2,良好的扩展性

    当你的计算机资源不能得到满足的时候,你可以通过简单的增加机器扩展它的计算能力。

    3,高容错性

    MapReduce设计的初衷就是使程序能够部署在廉价的pc机器上,这就是要求它具有很高的容错性。比如其中一台机器挂了,它可以把上面的机任务转移到另一个节点上运行,不至于这个任务运行失败,而且这个过程不需要人工参与,而完全是由hadoop内部完成的。

    4,适合pb级以上海量数据的离线处理

    可以实现上千台服务器集群并发工作,提供数据处理能力。

    缺点:

    1不擅长实时计算

    MapReduce无法像mysql一样,在毫秒或者秒级内返回结果。

    2,不擅长流式计算

    流式计算的输入数据是动态的,而MapReduce的输入数据集是静态的,不能动态变化。这是因为MapReduce自身的设计特点决定了数据源必须是静态的。

    3,不擅长DAG(有向图)计算

    多个应用程序存在依赖关系,后一个应用程序的输入为前一个的输出。在这种情况下MapReduce并不是不能做,而是使用后,每个MapReduce作业的输出结果都会写入磁盘,会造成大量的磁盘IO,导致性能非常的低下。

    2.mapreduce的数据类型

    Java类型

    Hadoop Writable类型

    Boolean

    BooleanWritable

    Byte

    ByteWritable

    Int

    IntWritable

    Float

    FloatWritable

    Long

    LongWritable

    Double

    DoubleWritable

    String

    Text

    Map

    MapWritable

    Array

    ArrayWritable

    hadoop序列化:
    序列化:将对象序列化成字节序列 (方便磁盘存储和网络传输)
    反序列化:将字节序列转换成对象

    hadoop的序列化的优点:(只对数据进行序列化)
    紧凑 快速 可扩展 可以跨语言交互

    序列化
    步骤1:
    使用Writer接口
    implements Writable
    步骤2
    /**
    * 注意点:
    * 1.序列化数据的时候,序列化的数据类型要对应
    * write这个是hadoop提供的序列化方法
    * @param dataOutput
    * @throws IOException
    */
    public void write(DataOutput dataOutput) throws IOException {

    }

    /**
    * 注意点:
    * 一定要注意反序列化变量赋值的顺序,要和序列化顺序保持一致
    * readFields :hadoop 提供的反序列化方法
    * @param dataInput
    * @throws IOException
    */
    public void readFields(DataInput dataInput) throws IOException {

    }

    job的提交流程:
    waitForCompletion提交任务的入口方法
    this.submit(); 提交job任务
    this.ensureState(Job.JobState.DEFINE);再次确认我们job的状态(DEFINE)
    this.connect();判断任务是在本地运行还是远程集群中运行(连接yarn)
    submitter.submitJobInternal() 任务提交者提交任务
    this.checkSpecs(job); 检查文件的输出路径是否存在
    checkOutputSpecs()检查文件的输出路径是否存在,没有设置报异常,已经存在也报异常
    addMRFrameworkToDistributedCache(conf); 将配置信息加载到分布式缓存中
    this.submitClient.getNewJobID(); 获取一个任务的id
    this.writeSplits(job, submitJobDir);获取切片数量,并将切片文件信息写入到submitJobFile文件夹下
    this.writeConf(conf, submitJobFile);将配置信息写入到submitJobFile文件夹下

    this.submitClient.submitJob 真正提交job任务

    this.state = Job.JobState.RUNNING;任务提交完毕,将状态改为RUNNING

    this.isSuccessful();任务执行成功还是失败:返回true表示任务执行成功,返回flase任务执行失败

    FileInputFormat
    getSplits:1.如何进行切片 2.可不可以切片this.isSplitable(job, path)
    for(bytesRemaining = length; (double)bytesRemaining / (double)splitSize > 1.1D; bytesRemaining -= splitSize) {
    blkIndex = this.getBlockIndex(blkLocations, length - bytesRemaining);
    splits.add(this.makeSplit(path, length - bytesRemaining, splitSize, blkLocations[blkIndex].getHosts(), blkLocations[blkIndex].getCachedHosts()));
    }

    if (bytesRemaining != 0L) {
    blkIndex = this.getBlockIndex(blkLocations, length - bytesRemaining);
    splits.add(this.makeSplit(path, length - bytesRemaining, bytesRemaining, blkLocations[blkIndex].getHosts(), blkLocations[blkIndex].getCachedHosts()));
    }

    如何自定义设置切片的大小参考课件3.1.3 默认情况下切片的切块大小是块大小128M



    hadoop自带得inputformat
    TextInputFormat 使用得是FileInput..得切片方法 LineRecordReader(将文件以kv值得形式返回)
    NLineInputFormat 自定义了切片方法(按行切片) LineRecordReader
    CombineTextInputFormat 自定义了切片方法(按照设置得大小切片) CombineFileRecordReader
    FixedLengthInputFormat 使用得是FileInput..得切片方法 FixedLengthRecordReader(返回得都是固定长度得value)

    KeyValueTextInputFormat 使用得是FileInput..得切片方法 KeyValueLineRecordReader(key是一行中得第一个单词,value是一行中除了第一个单词之后得字符串)
    SequenceFileInputFormat 使用得是FileInput..得切片方法 SequenceFileRecordReader(二进制得数据)

    注意一般情况下够用,但是特殊情况需要我们自定义
    自定义inputformat首先得明确key value值得输出(作为mapper得输入得key value)
    (1)自定义inputformat继承extends FileInputFormat<key,value>
    @Override
    protected boolean isSplitable(JobContext context, Path filename) {
    //返回true或者false:表示是否允许切片
    }

    @Override
    public RecordReader<org.apache.hadoop.io.Text, BytesWritable> createRecordReader(InputSplit inputSplit, TaskAttemptContext taskAttemptContext) throws IOException, InterruptedException {
    返回一个RecordReader(key value值)
    }
    (2)自定义RecordReader继承extends RecordReader<key,value>
    实现6个方法,见代码
    /**
    * 框架运行的时候,执行一次
    * @param inputSplit
    * @param taskAttemptContext
    * @throws IOException
    * @throws InterruptedException
    */
    @Override
    public void initialize(InputSplit inputSplit, TaskAttemptContext taskAttemptContext) throws IOException, InterruptedException {
    fs = (FileSplit) inputSplit;
    //获取文件的路径
    Path path = fs.getPath();
    //获取配置实例的对象
    Configuration configuration = taskAttemptContext.getConfiguration();
    //文件操作系统实例对象
    fileSystem = path.getFileSystem(configuration);
    }

    /**
    * 判断文件是否读完(是否还有下一组kv),
    * @return 返回true表示存在下一组kv,返回false,表示不存在下一组kv
    * @throws IOException
    * @throws InterruptedException
    */
    @Override
    public boolean nextKeyValue() throws IOException, InterruptedException {

    }

    /**
    * 获取当前的key
    * @return 返回当前的key
    * @throws IOException
    * @throws InterruptedException
    */
    @Override
    public Text getCurrentKey() throws IOException, InterruptedException {

    }

    /**
    * 获取当前的value
    * @return 返回当前的value
    * @throws IOException
    * @throws InterruptedException
    */
    @Override
    public BytesWritable getCurrentValue() throws IOException, InterruptedException {

    }

    /**
    * 获取读取文件的进度
    * @return
    * @throws IOException
    * @throws InterruptedException
    */
    @Override
    public float getProgress() throws IOException, InterruptedException {


    }

    /**
    * 执行完毕,走close方法
    * @throws IOException
    */
    @Override
    public void close() throws IOException {

    }

    (3)设置和使用自定义得inputformat(在driver类中)
    //设置自定义的InputFormat
    job.setInputFormatClass(xxxFileInputFormat.class);

    inputformat主要得工作:
    (1)文件得切片
    (2)将输入文件转换为key value值,输出到mapper

    mapreduce得流程图,自己去看一下(以后要达到会画得程度)。

    分区:分数得数量对应着reducetask得数量,有几个分区就有几个输出文件

    系统默认得分区,是随机分配得
    可以自定义分区,将数据写入到指定分区中(文件中)

    public class Mypartitioner extends Partitioner<Text,FlowBean> {
    @Override
    public int getPartition(Text text, FlowBean flowBean, int i) {
    //对不同得手机号进行处理,把不同得数据写入到指定得分区下
    String phone = text.toString();
    switch (phone.substring(0,3)){
    case "138":
    return 0;
    case "139":
    return 1;
    case "135":
    return 2;
    case "150":
    return 3;
    default:
    return 4;
    }
    }
    }

    设置reduceTask得数量
    job.setNumReduceTasks(5);
    设置自定义分区:
    job.setPartitionerClass(xxxMypartitioner.class)

    注意:
    设置得reduceTask得数量(分区数)跟自定义分区分配分区时得值对应
    注意分区号从0开始,不要跳号

     MapReduce工作流程

     

     

  • 相关阅读:
    浅谈页面中的焦点
    简单的jQuery幻灯片实现
    从is(":checked")说起
    通过Javascript得到URL中的参数(query string)
    Javascript设置对象属性为"只读"
    Javascript判断两个日期是否相等
    利用HttpWebRequest访问WebApi
    利用Newtonsoft.Json实现Json序列化与反序列化
    在ASP.NET MVC中以post方式传递数组参数的示例
    SQL Server 锁表、查询被锁表、解锁相关语句
  • 原文地址:https://www.cnblogs.com/lu0420-0412/p/12112020.html
Copyright © 2011-2022 走看看