压缩与存储格式

压缩

压缩是调优的重要的点。
另外不一定非要用带split的压缩方式,如果前期做的比较好,每个块都分割成128M(一般是比block块小一点,比如256M就放250M),就可以不用带split的压缩了。

文件的存储格式

Hive可以支持多种格式,主要有:SEQUENCEFILE,TEXTFILE,RCFILE,ORCPARQUET。其中Hive默认的文件格式是TextFile。
设定文件格式的语句是:

CREATE TABLE tt2 (
id int,
name string
) ROW FORMAT DELIMITED FIELDS TERMINATED BY "\t"
STORED AS TEXTFILE;

CREATE TABLE tt3 (
id int,
name string
) ROW FORMAT DELIMITED FIELDS TERMINATED BY "\t"
STORED AS 
INPUTFORMAT 'org.apache.hadoop.mapred.TextInputFormat'
OUTPUTFORMAT 'org.apache.hadoop.hive.ql.io.HiveIgnoreKeyTextOutputFormat';

上面两个语句创建的表的存储格式与下面的格式是相同的
CREATE TABLE tt (
id int,
name string
) ROW FORMAT DELIMITED FIELDS TERMINATED BY "\t";

行式存储与列式存储

行式存储

一整条数据在一个block里面

优点:读取全部数据(select *)的时候,可以直接从block里面获取。
缺点:每个字段的类型可能不同,比如:有int,string,date,boolean等等,由于所有的字段存放在一起,在压缩的时候性能就不够好。
读取全部的时候直接读取,但是select id等等某些字段的时候,就需要把所有的行都读取进来,然后再找id,因为不能跳过数据,所以占用磁盘IO,花费较多的时间,导致效率不够高。

列式存储

某些列存在一个block里面(可能是两列,也可能是一列,一列就是一个字段)

优点:当读取部分列的时候,可以只读一部分block而不用全部读取。
缺点:使用select * 来查询或者查询字段比较多的时候,所有的block数据需要重组,占用IO。

对于大数据来说,大部分的表都只用部分字段。

存储格式比较

TextFile

默认文本类型,解析起来比较麻烦,但是通用性比较好。

SEQUENCEFILE

key-value存储,SequenceFile相比TextFile 多了一些冗余信息(头(Header),Sync什么的,用来记录key-value的长度,比如:总长10,key长4,那么读取value的时候就可以直接读取另外6个),可以搜索这个存储的图片,方便理解。

对于压缩,SEQUENCEFILE压缩的地方是value(Compressed value)
优点是随机读写性能好一些,因为可以跳过一些地方直接读value

Hive创建了一个存储格式为SEQUENCEFILE的表,那么在导入数据的时候就不能直接从本地导入TextFile(文本文件)格式的文件,可以通过导入一个同样schema的中间表(TextFile)来过渡。

CREATE TABLE tt_rcfile (
id int,
name string
) ROW FORMAT DELIMITED FIELDS TERMINATED BY "\t"
STORED AS SEQUENCEFILE;

insert into table tt4 select * from tt;
RCFILE

Record(记录) Columnar(列式) File,是一个列式存储的格式。
其实只能提升10%的存储(大小减少10%),而且是行列混合的(可以上网上搜图),先是行式存储成row group,然后在里面按列存储

ORC

会对数据做索引,当查询语句含有一定条件的时候,就可能会跳过一些数据,从而减少IO。https://cwiki.apache.org/confluence/display/Hive/LanguageManual+ORC

create table tt_orc
ROW FORMAT DELIMITED FIELDS TERMINATED BY "\t"
STORED AS ORC 
TBLPROPERTIES("orc.compress"="NONE")
as select * from tt;

create table tt_orc_zlib
ROW FORMAT DELIMITED FIELDS TERMINATED BY "\t"
STORED AS ORC 
TBLPROPERTIES("orc.compress"="ZLIB")
as select * from tt;

即设置了存储格式又设置了压缩。(压缩默认是zlib)
将原大小18.1M的文本文件变为7.7M(没使用压缩),2.8M(zlib压缩)。

PARQUET

https://cwiki.apache.org/confluwnce/display/Hive/Parquet
使用这个存储格式,可以将原大小18.1M的文本文件变为13.1M(没有使用压缩),自己定义压缩(gzip,snappy等等):

set parquet.compression=gzip;
create table tt_parquet_gzip
ROW FORMAT DELIMITED FIELDS TERMINATED BY "\t"
STORED AS PARQUET 
as select * from tt;

压缩后文件大小为3.9M

对比

数据量小,对比不出来时间上的差距,可以查看MapReduce运行完成后读取的数据量:

select count(1) from tt where id='B58W48U4WKZCJ5D1T3Z9ZY88RU7QA7B1';
HDFS Read:19022700(MapReduce执行完毕后会在后几行显示出来这个信息)

select count(1) from tt_rcfile where id='B58W48U4WKZCJ5D1T3Z9ZY88RU7QA7B1';
3725391

select count(1) from tt_orc where id='B58W48U4WKZCJ5D1T3Z9ZY88RU7QA7B1';
1810082

select count(1) from tt_orc_zlib where id='B58W48U4WKZCJ5D1T3Z9ZY88RU7QA7B1';
1257539

select count(1) from tt_parquet where id='B58W48U4WKZCJ5D1T3Z9ZY88RU7QA7B1';
2687025

select count(1) from tt_parquet_gzip where id='B58W48U4WKZCJ5D1T3Z9ZY88RU7QA7B1';
1624507

ORC查询数据量少的原因是因为predicate pushdown (谓词下压)。

所以,做好的组合是:
ORC/PARQUET + COMPRESSION(orc或者parquet格式,再加上压缩)

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值