上一篇(ch.9)

下一篇(ch.11)

第三部分 派生数据

  存储和处理数据的系统分为:记录系统和派生系统,后者可视为冗余部分,以前者为准;

第十章 批处理系统

  web这种交互模式并不是唯一的系统类型,一般有三种类型的系统:

  在线服务,服务端等待客户端的请求,收到请求后尽快返回响应,以平均响应时间为性能指标(包括可用性);

  批处理系统离线系统),接收一批静态、历史的、预先存在的数据,处理执行相当一段时间,客户端不会等待其响应,通常定时执行处理该批量数据,以吞吐量为性能指标(处理数据的耗时);

  流处理系统近实时系统),处理连续不断到达的实时数据,数据是以事件的形式流入系统,相比批处理系统,执行延迟更低;

unix上的批处理

最大的局限性是只能运行在单机上;

cat /var/log/nginx/access.log |
    awk '{print $7}'sortuniq -c          |
    sort-r -nhead -n 5
  • line 1,读取日志文件;
  • line 2,将每行按照空格分割为不同的部分,且仅输出第七部分,即请求的url地址;
  • line 3,按照字母顺序排列url地址列表;
  • line 4,检查相邻行是否相同,过滤掉重复行,并输出一个计数器,计数不同的url的出现次数;
  • line 5,按照每行的起始处的数字排序(计数值),降序返回结果;
  • line 6,只输出结果的前五行;

常用命令:awk、sed、grep、sort、xargs

统一的接口

  使用管道串联时,不同程序对应的输入输出需要兼容的接口,在unix中即为文件(文件描述符)

  即使是相同数据模型的数据库,做数据迁移也不容易,因为继承性的缺失导致了数据的巴尔干化,即数据被割裂、分散在多个地方(因为没有统一接口);

MapReduce和分布式文件系统

  hdfs 通过网络连接,在每台机器上都有一个守护进程,开放一个网络服务供其他节点访问该机器上的文件;

  namenode 作为中央服务器,管理追踪文件块存储在哪台机器上(包括副本);

reduce端的join和分组

  通常reduce处理后的事件,或者流数据,在分析任务时可能需要和 当前处理的数据 和 数据库中的信息 相关联,即使用 join 操作;

  最简单的 join 就是遍历当前处理的事件,再去数据库根据唯一标识进行查询,很明显性能极差;

  优化的方法,将数据库数据提前备份到hdfs,再由MapReduce集中所有有关数据;

理数据倾斜

  即某个关键字的相关数据量很大,导致单个 reducer 处理的数据量明显比其他的 reducer片多,防止延迟当前作业的完成时间;

  hive 的优化为,提前在元数据识别出热点,在map端进行join;

  可以分阶段执行聚合热点,每阶段聚合一部分数据,最后合并为单一值;

map端join

  • 在Map阶段,Mapper节点会将本地的数据和广播的小数据集进行Join操作。这样可以避免在Reduce阶段的大量数据传输;

广播哈希join

  大数据集中每个分区读取整个小数据集,多个map任务;

即:

  • 当其中一个数据集很小(足够装入内存)时,可以将这个小数据集广播给所有的Mapper节点;

分区哈希join

  即对输入map的数据进行分区,即将分类的数据,和对应的哈希关系(映射关系,如对外键哈希分区)

  多个数据源的分区策略必须一致;

  在hive中被称为 backeted map join;

排序join

  如果输入的数据集已经按照Join的Key进行排序,Mapper可以直接读取两个有序的数据集并执行类似于归并排序的Join操作;

  即原本不能确定全局顺序,现在可以区分出输入数据集各自的顺序时,就可以使用归并如依次寻找最小值去合并(性能好),最后的结果是有序的;

批处理工作流的输出

生成倒排索引

  mapper对文档进行分区(分词计数等),reducer构建分区索引,并写入分布式文件系统;

构建机器学习系统,如分类器,推荐系统等;

  mapreduce 如果直接读写数据库,那么数据库可能会过载,且影响查询性能,通常满足一个大任务,全有或全无;

  则写入分布式文件系统内更佳,数据文件写入后就是不可变的;

进一步

中间状态实体化(如 RDD)

  一个大任务内会有多个作业,可能有依赖顺序,即中间状态可能被多个任务依赖,可持久化,避免重复计算;

数据流引擎

  如spark,flink等;

  他们将整个工作流都看做一个作业,同样对输入分区并行处理,输出会被复制到网络上成为另一个RDD的输入;

  工作流所需的数据和join都是明确声明的,即由调度器去做本地优化,如拉近输出和输入的距离;

  中间状态的持久化不是写入分布式文件系统(被复制会浪费),而是写入磁盘或本地内存;

  任务开始执行的时机是其输入条件准备完成即可,不需要等上一阶段的任务全完成后才开始;

  spark通过血统图,重新计算丢失数据;