压缩在hadoop中的应用

压缩在hadoop中的应用

1.1压缩简介
Hadoop 作为一个较通用的海量数据处理平台,每次运算都会需要处理大量数据,我们会在 Hadoop 系统中对数据进行压缩处理来优化磁盘使用率,提高数据在磁盘和网络中的传输速度,从而提高系统处理数据的效率。在使用压缩方式方面,主要考虑压缩速度和压缩文件的可分割性。综合所述,使用压缩的优点如下:
1. 节省数据占用的磁盘空间;
2. 加快数据在磁盘和网络中的传输速度,从而提高系统的处理速度。

常用的压缩技术有两种,一种是无损压缩(Lossless compression),一种是有损压缩(Lossy compression),无损压缩后文件内容不会丢失,解压后和源文件一模一样,而有损压缩后文件内容会丢失。
这里写图片描述

1.2压缩格式
Hadoop 对于压缩格式的是自动识别。如果我们压缩的文件有相应压缩格式的扩展名(比如 lzo,gz,bzip2 等)。Hadoop 会根据压缩格式的扩展名自动选择相对应的解码器来解压数据,此过程完全是 Hadoop 自动处理,我们只需要确保输入的压缩文件有扩展名。

常用压缩格式介绍:

压缩格式 工具 算法 扩展名 可分割性
gzip gzip DEFLATE .gz
bzip2 bzip2 bzip2 .bz2
LZO lzop LZOP .lzo Yes if indexed(是,在文件范围内)
Snappy N/A Snappy .snappy

常用压缩格式对比(环境、条件设置如下):
8 core i7 CPU
8GB memory
64 bit CentOS
1.4GB Wikipedia Corpus 2-gram text input

使用不同的压缩格式,压缩之后对比如图:
这里写图片描述

常用压缩格式对比
这里写图片描述

总结:使用压缩可以减少磁盘空间、IO及网络宽带,但是会提高CPU的利用率,压缩比与压缩速度成反比,压缩比越高,压缩速度越慢

这里写图片描述

具体的压缩对比,以及使用场景,请参考:http://www.linuxidc.com/Linux/2014-05/101230.htm

1.3在MapReduce上使用压缩
如何在MapReduce中使用压缩?
1.输入的文件的压缩

如果输入的文件是压缩过的,那么在被MapReduce读取时,它们会被自动解压,根据文件扩展名来决定应该使用哪一个压缩解码器。

2.MapReduce作业的输出的压缩

如果要压缩MapReduce作业的输出,请在作业配置文件中将mapred.output.compress属性设置为true。将mapred.output.compression.codec属性设置为自己打算使用的压缩编码/解码器的类名。

如果为输出使用了一系列文件,可以设置mapred.output.compression.type属性来控制压缩类型,默认为RECORD,它压缩单独的记录。将它改为BLOCK,则可以压缩一组记录。由于它有更好的压缩比,所以推荐使用。

3.map作业输出结果的压缩

即使MapReduce应用使用非压缩的数据来读取和写入,我们也可以受益于压缩map阶段的中间输出。因为map作业的输出会被写入磁盘并通过网络传输到reducer节点,所以如果使用LZO之类的快速压缩,能得到更好的性能,因为传输的数据量大大减少了。以下代码显示了启用map输出压缩和设置压缩格式的配置属性。

conf.setCompressMapOutput(true);
conf.setMapOutputCompressorClass(GzipCodec.class);

压缩在MapReduce中的应用
这里写图片描述

这里写图片描述

(1).Use Compressed Map Input
map的输入建议使用支持分割的压缩,比如Bzip2,因为可以并行处理

(2).Compress Intermediate Data
中间数据的压缩建议使用压缩速度快的,比如Snappy、LZO,可以节省时间,提高效率

(3).Compress Reducer Output
Reduce的输出建议使用压缩比较高的压缩,压缩后文件较小,减少磁盘空间。

hadoop使用压缩的前提是:编译hadoop源码,输入如下命令来检查hadoop是否支持压缩

$ hadoop checknative

如果看到如下图一样的效果,表示hadoop中可以使用压缩
这里写图片描述
如果执行之后出现如图所示(false结果),则请参考:http://blog.csdn.net/qq_38799155/article/details/77881482
这里写图片描述

案例:统计单词出现的次数

新建文件hello.txt并编辑文件内容如下

vi hello.txt
hello hadoop
hello mapreduce
hello zookeeper
hello hbase
hello hive

上传文件到hdfs:

$ hadoop fs -mkdir -p /user/hadoop/input
$ hadoop fs -put hello.txt input/
$ hadoop fs -ls 
$ hadoop fs -text input/*

这里写图片描述

进入hadoop-mapreduce-examples-2.7.3.jar所在目录

$ cd /home/hadoop/hadoop-2.7.3/share/hadoop/mapreduce

这里写图片描述

  • 不使用压缩的效果
$ hadoop jar hadoop-mapreduce-examples-2.7.3.jar wordcount input/ output/

查看结果

$ hadoop fs -ls output/
$ hadoop fs -cat output/part-r-00000

这里写图片描述

  • 使用压缩的效果

    hadoop 中使用压缩需要进行配置,有两种方式,一种配置在hadoop的配置文件中,一种直接在命令中指定参数即可,笔者使用第二种方式,如果配置在文件中,请按如下操作

在hadoop的配置文件里添加
1.core-site.xml

<property>
    <name>io.compression.codecs</name>
    <value>
      org.apache.hadoop.io.compress.GzipCodec,
      org.apache.hadoop.io.compress.DefaultCodec,
      org.apache.hadoop.io.compress.BZip2Codec
    </value>
</property>

2 mapred-site.xml

<property>
    <name>mapreduce.output.fileoutputformat.compress</name>
    <value>true</value>
</property>

<property>
    <name>mapreduce.output.fileoutputformat.compress.codec</name>
    <value>org.apache.hadoop.io.compress.BZip2Codec</value>
</property>

<property>
    <name>mapreduce.map.output.compress</name>
    <value>true</value>
</property>

<property>
    <name>mapreduce.map.output.compress.codec</name>
    <value>org.apache.hadoop.io.compress.BZip2Codec</value>
</property>

使用MapReduce 压缩统计单数出现的次数,执行命令(执行前先删除output文件或者改一下输出的路径)

$ hadoop jar hadoop-mapreduce-examples-2.7.3.jar wordcount -Dmapreduce.output.fileoutputformat.compress=true -Dmapreduce.output.fileoutputformat.compress.codec=org.apache.hadoop.io.compress.BZip2Codec -Dmapreduce.map.output.compress=true -Dmapreduce.map.output.compress.codec=org.apache.hadoop.io.compress.BZip2Codec input/ output1/

查看结果

$ hadoop fs -ls output/
$ hadoop fs -text output/part-r-00000.bz2

这里写图片描述

笔者推荐:
Hadoop压缩API应用实例,请参考:http://book.51cto.com/art/201304/390240.htm

Hadoop在MapReduce中使用压缩详解,请参考:http://developer.51cto.com/art/201204/331337.htm

posted @ 2017-09-07 12:28  ZC_Surpass  阅读(273)  评论(0编辑  收藏  举报