前面精彩文章
HADOOP常用文件格式详解(一)
HADOOP常用文件格式详解(二)
前面介绍了HADOOP常用文件格式包括行式存储,列式存储,混合存储等等。
混合式文件存储融合了行存储和列存储的各自的优点。首先将记录表按照行进行分组,若干行为一组,对于每组内的所有记录在实际存储的时候按照列将同一列的内容连续存储在一起。
本文将详细介绍典型的混合存储方案-ORCFile。
ORC File,全名是Optimized Row Columnar (ORC) file,是HortonWorks工程师O‘Malley是贡献到hive上的一种数据存储格式Orcfile(Optimized Row Columnar),hive0.11开始支持 。
和RCFile类似,一些row为一个存储块,块内每列按照列存储,但是对RCFile做了一些优化。它的设计目标是来克服Hive其他格式的缺陷,供一种高效的方法来存储Hive数据。运用ORC File可以提高Hive的读、写以及处理数据的性能。
从上图可以看出ORC File包含3部分:Stripe、File Footer、PostScript。
PostScript:
记录了整个文件的压缩类型以及FileFooter的长度信息等。在读取文件时,会seek到文件尾部读PostScript,从里面解析到File Footer长度,再读FileFooter,从里面解析到各个Stripe信息,再读各个Stripe,即从后往前读。
File Footer:
包含了该ORC File文件中stripes的信息,每个stripe中有多少行,以及每列的数据类型。当然,它里面还包含了列级别的一些聚合的结果,比如:count, min, max, and sum。
Stripe:
每个Orc文件由1个或多个stripe组成,每个stripe默认大小250MB。每个Stripe里有三部分组成,分别是Index Data,Row Data,Stripe Footer。
Stripe 结构Stripe 包含三部分:Index Data、Row Data、Stripe Footer。
Index Data:
包含每列的最大和最小值以及每列所在行的位置。为了进一步的避免读入不必要的数据,在逻辑上将一个column的index按照一定的行数间隔构建偏移量。通过偏移量,可以在stripe中快速读取的过程中可以跳过很多行。默认行数为10000,可由参数配置。
Row Data:按列存储的压缩数据。
Stripe Footer:存的是各个Stream的类型,长度等信息
Stream:一个stream表示文件中一段有效的数据,包括索引和数据两类。索引stream保存每一个row group的位置和统计信息,数据stream包括多种类型的数据,具体需要哪几种是由该列类型和编码方式决定。
复杂数据类型ORC可以支持复杂的数据结构。
类型 | |
Array | 一个包含所有数组元素的子字段 |
map | 两个子字段,一个key字段,一个value字段 |
Struct | 每一个属性对应一个子字段 |
Union | 每一个属性对应一个子字段 |
对于复杂数据类型,比如Map,ORC文件会将一个复杂数据类型字段解析成多个子字段。
当字段类型都被解析后,会由这些字段类型组成一个字段树,只有树的叶子节点才会保存表数据,这些叶子节点中的数据形成一个数据流,如上图中的Data Stream。
为了使ORC文件的reader更加高效的读取数据,字段的metadata会保存在Meta Stream中。在字段树中,每一个非叶子节点记录的就是字段的metadata,比如对一个array来说,会记录它的长度。下图根据表的字段类型生成了一个对应的字段树。
HIVE使用ORCFile可以在hive定义表或者分区的时候定义。例如下面的HIVE SQL:
CREATE TABLE ... STORED AS ORC
ALTER TABLE ... [PARTITION partition_spec] SET FILEFORMAT ORC
SET hive.default.fileformat=Orc
ORCFile存储格式有几个表属性可以进一步改善效果,这些属性如下:
属性 | 默认值 | 说明 |
orc.compress | ZLIB | 列压缩格式(NONE, ZLIB, SNAPPY) |
orc.compress.size | 262,144 (= 256 KiB) | 每一个压缩块大小 |
orc.stripe.size | 268,435,456 (= 256 MiB) | 每一个stripe大小 |
ORCFile 提供非常出色压缩比。下图展示了,针对一个TPC-DS 数据集(500G)各种文件格式的压缩比。数据集中的数据是随机产生的包括字符串、浮点数等。
ORCFile之所以有这么高的压缩比和他提供的一系列压缩算法分不开:run-length encoding(run-length编码),dictionary encoding(字典编码)。
总结使用ORC文件格式时,用户可以使用HDFS的每一个block存储ORC文件的一个stripe。对于一个ORC文件来说,stripe的大小一般需要设置得比HDFS的block小,如果不这样的话,一个stripe就会分别在HDFS的多个block上,当读取这种数据时就会发生远程读数据的行为。如果设置stripe的只保存在一个block上的话,如果当前block上的剩余空间不足以存储下一个strpie,ORC的writer接下来会将数据打散保存在block剩余的空间上,直到这个block存满为止。这样,下一个stripe又会从下一个block开始存储。
和RCFile格式相比,ORC File格式有以下优点:
(1)、支持各种复杂的数据类型,比如: datetime, decimal, 以及一些复杂类型(struct, list, map, and union);
(2)、在文件中存储了一些轻量级的索引数据;
(3)、基于数据类型的块模式压缩:a、integer类型的列用行程长度编码(run-length encoding);b、String类型的列用字典编码(dictionary encoding);