六、期中大作业
1. 面试题
1.1 简述Hadoop小文件弊端
- 当小文件比较多的时候,就会产生很多的元数据文件,一方面会大量占用NameNode的内存空间,另一方面就是元数据文件过多,使得寻址索引速度变慢。小文件过多,在进行MR计算时,会生成过多切片,需要启动过多的MapTask。每个MapTask处理的数据量小,导致MapTask的处理时间比启动时间还小,白白消耗资源。
- 解决方案:
- 数据源头控制小文件出现:在数据采集的时候,就将小文件或小批数据合成大文件再上传HDFS
- 在业务处理之前:在HDFS上使用MapReduce程序对小文件进行合并。
- 在MapReduce处理时,可采用CombineTextInputFormat提高效率
1.2 HDFS中DataNode挂掉如何处理
- 关闭pipeline(通信管道)
- 根据ack queue将已经发送的pocket添加回data queue(撤回已经发送到故障节点的pocket)
- namenode记录故障节点中的未完成的block信息, 待节点恢复后, 删除这部分数据
- 在剩余的节点上建立新的通信管道
- 继续传输pocket
- datanode挂掉后缺失的副本会namenode管理下恢复
1.3 HDFS中NameNode挂掉如何处理
- 如果只配置了一个NameNode作为主节点
- 方法一:拷贝SNN数据到NN存储数据的目录中
- kill -9 NameNode进程
- 删除NameNode存储的数据
- 拷贝SecondaryNameNode中数据到原NameNode存储数据目录
- 重新启动NameNode即可
- 方法二:使用-importCheckpoint选项启动NN守护进程,它会将SNN数据拷贝到NN数据目录中
- 修改hdfs-site.xml
- kill -9 NameNode进程
- 删除NameNode存储的数据
- 拷贝SecondaryNameNode中数据到原NameNode存储数据目录并删除in_use.lock文件
- 导入检查点数据
- 启动NameNode
- 方法一:拷贝SNN数据到NN存储数据的目录中
1.4 HBase读写流程
- HBase写流程:
- Client访问zookeeper,获取元数据存储所在的regionserver
- 通过刚刚获取的地址访问对应的regionserver,拿到对应的表存储的regionserver
- 去表所在的regionserver进行数据的添加
- 查找对应的region,在region中寻找列族,先向memstore中写入数据
- 当memstore写入的值变多,触发溢写操作(flush),进行文件的溢写,成为一个StoreFile
- 当溢写的文件过多时,会触发文件的合并(Compact)操作
- 当region中的数据逐渐变大之后,达到某一个阈值,会进行裂变(一个region等分为两个region,并分配到不同的regionserver),原本的Region会下线,新Split出来的两个Region会被HMaster分配到相应的HRegionServer上,使得原先1个Region的压力得以分流到2个Region上。
- HBase读流程:
- Client访问zookeeper,获取元数据存储所在的regionserver
- 通过刚刚获取的地址访问对应的regionserver,拿到对应的表存储的regionserver
- 去表所在的regionserver进行数据的读取
- 查找对应的region,在region中寻找列族,先找到memstore,找不到去blockcache中寻找,再找不到就进行storefile的遍历
- 找到数据之后会先缓存到blockcache中,再将结果返回
1.5 MapReduce为什么一定要又Shuffle过程
- Shuffle使map和reduce之间的桥梁,reduce需要Shuffle来获取数据
1.6 MapReduce中的三次排序
- 不是很能理解题目的意思,有点疑惑
1.7 MapReduce为什么不能产生过多小文件
- 文件的元数据存储在namenode中,每个文件的元数据都差不多大,小文件过多会极大的占用namonode
的内存,制约集群的扩展。(主要影响) - 在对小文件进行处理的时候,一个小文件对应一个maptask,一个maptask会开启一个JVM进程,JVM处理一个maptask后会关闭,这样JVM开关的时间会比处理maptask的时间更长,严重浪费了资源,因为进程的开启销毁会严重性能。
- HDFS读写小文件时也会更加耗时,因为每次都需要从NameNode获取元信息,并且对应的DataNode建立连接