溫馨提示×

您好,登錄后才能下訂單哦!

密碼登錄×
登錄注冊(cè)×
其他方式登錄
點(diǎn)擊 登錄注冊(cè) 即表示同意《億速云用戶服務(wù)條款》

十七、hadoop壓縮相關(guān)

發(fā)布時(shí)間:2020-07-18 15:05:34 來(lái)源:網(wǎng)絡(luò) 閱讀:362 作者:隔壁小白 欄目:大數(shù)據(jù)

一、數(shù)據(jù)壓縮在hadoop中的意義

1、基本概述

? 壓縮技術(shù)可以減少底層hdfs的讀寫字節(jié)數(shù)。并且能夠降低在數(shù)據(jù)傳輸過(guò)程中占用的網(wǎng)絡(luò)帶寬資源,以及降低占用的磁盤空間。而在MapReduce中,shuffle以及merge過(guò)程都面臨著巨大的IO壓力。但是要注意增加了壓縮,另外一方面會(huì)增加cpu的負(fù)載。所以在要權(quán)衡好是否采用壓縮,以及采用的壓縮算法的特性。

2、壓縮應(yīng)用基本原則

運(yùn)算密集型的job,少用壓縮。因?yàn)閴嚎s占用cpu。
IO密集型的job,可用壓縮減少數(shù)據(jù)量。
選擇壓縮算法時(shí),要注意壓縮比,壓縮比越大,壓縮以及解壓時(shí)間越長(zhǎng)。

二、MR支持的壓縮編碼格式

1、壓縮編碼

壓縮格式 hadoop是否自帶 算法 文件擴(kuò)展名 可否可切分 換成壓縮格式后,原來(lái)的程序是否需要修改
DEFAULT DEFAULT .deflate 與普通文本處理一樣,不需要修改
gzip DEFAULT .gz 與普通文本處理一樣,不需要修改
bzip2 bzip2 .bz2 與普通文本處理一樣,不需要修改
LZO 需另外安裝 lzo .lzo 需要建立索引文件,還需要指定輸出格式
snappy 需另外安裝 snappy .snappy 與普通文本處理一樣,不需要修改

2、不同壓縮算法對(duì)應(yīng)的編解碼器

壓縮格式 對(duì)應(yīng)編解碼器
DEFAULT org.apache.hadoop.io.compress.DefaultCodec
gzip org.apache.hadoop.io.compress.GzipCodec
bzip2 org.apache.hadoop.io.compress.BZip2Codec
lzo com.hadoop.compression.lzo.LzopCodec
snappy org.apache.hadoop.io.compress.SnappyCodec

3、不同壓縮算法的特性以及適用場(chǎng)景

(1)gzip

優(yōu)點(diǎn):
壓縮率高,解壓、壓縮速度也必比較快。hadoop本身自帶,在應(yīng)用中處理gzip格式的文件就和直接處理文本一樣。大部分Linux自帶gzip命令,使用方便。

缺點(diǎn):不支持split

適用場(chǎng)景:
當(dāng)每個(gè)文件壓縮之后在一個(gè)block左右的大?。ㄒ?yàn)闊o(wú)法分片),都可以考慮使用gzip將原數(shù)據(jù)壓縮。例如可以將一天或者一小時(shí)的日志壓縮成一個(gè)gzip文件,運(yùn)行MapReduce的時(shí)候就可以并行處理多個(gè)gzip。hive,streaming,MapReduce程序處理壓縮文件時(shí),無(wú)需修改程序,就像處理文本文件一樣。

(2)bzip2

優(yōu)點(diǎn):
支持split;高壓縮比,比gzip高。hadoop自帶,Linux下自帶bzip2命令

缺點(diǎn):壓縮、解壓速度慢,不支持native(java和C交互的api接口)

適用場(chǎng)景:
適合對(duì)速度要求不高,但需要較高的壓縮率的時(shí)候,可以作為mapreduce作業(yè)的輸出格式;或者輸出之后的數(shù)據(jù)比較大,處理之后的數(shù)據(jù)需要壓縮存檔減少磁盤空間并且以后數(shù)據(jù)用得比較少的情況;或者對(duì)單個(gè)很大的文本文件想壓縮減少存儲(chǔ)空間,同時(shí)又需要支持split,而且兼容之前的應(yīng)用程序(即應(yīng)用程序不需要修改)的情況。

(3)lzo

優(yōu)點(diǎn):
壓縮/解壓速度比較快,壓縮率合理(比gzip和bzip2?。?。支持split,是hadoop中最流行的壓縮格式??梢栽贚inux下可以通過(guò)安裝lzop命令來(lái)使用

缺點(diǎn):
壓縮率比gzip要低一些;hadoop本身不支持,需要安裝;在應(yīng)用中對(duì)lzo格式的文件需要做一些特殊處理(為了支持split需要建索引,還需要指定inputformat為lzo格式)。

適用場(chǎng)景:
一個(gè)很大的文本文件,壓縮之后還大于200M以上的可以考慮,而且單個(gè)文件越大,lzo優(yōu)點(diǎn)越越明顯。

(4)snappy

優(yōu)點(diǎn):壓縮和解壓速度快,合理的壓縮率
缺點(diǎn):不支持的split,壓縮率比gzip要低;hadoop本身不支持,需要安裝
適用場(chǎng)景:
當(dāng)Mapreduce作業(yè)的Map輸出的數(shù)據(jù)比較大的時(shí)候,作為Map到Reduce的中間數(shù)據(jù)的壓縮格式;或者作為一個(gè)Mapreduce作業(yè)的輸出和另外一個(gè)Mapreduce作業(yè)的輸入。

三、壓縮的配置

1、適用范圍

可以用在MapReduce的任意階段輸出、原始數(shù)據(jù)的壓縮、reduce的輸出等

2、hadoop壓縮配置參數(shù)

參數(shù) 默認(rèn)值 階段 建議
io.compression.codecs (在core-site.xml中配置) org.apache.hadoop.io.compress.DefaultCodec, org.apache.hadoop.io.compress.GzipCodec, org.apache.hadoop.io.compress.BZip2Codec 輸入壓縮 Hadoop使用文件擴(kuò)展名判斷是否支持某種編解碼器
mapreduce.map.output.compress(在mapred-site.xml中配置) false map輸出 這個(gè)參數(shù)設(shè)為true啟用壓縮
mapreduce.map.output.compress.codec(在mapred-site.xml中配置) org.apache.hadoop.io.compress.DefaultCodec mapper輸出 使用LZO或snappy編解碼器在此階段壓縮數(shù)據(jù)
mapreduce.output.fileoutputformat.compress(在mapred-site.xml中配置) false reduce輸出 這個(gè)參數(shù)設(shè)為true啟用壓縮
mapreduce.output.fileoutputformat.compress.codec(在mapred-site.xml中配置) org.apache.hadoop.io.compress. DefaultCodec reduce輸出 使用gzip或者bzip2來(lái)壓縮
mapreduce.output.fileoutputformat.compress.type(在mapred-site.xml中配置) RECORD reduce輸出 SequenceFile輸出使用的壓縮類型:NONE和BLOCK

四、壓縮應(yīng)用實(shí)戰(zhàn)例子

1、數(shù)據(jù)流的壓縮和解壓

package JavaCompress;

import org.apache.hadoop.conf.Configuration;
import org.apache.hadoop.fs.Path;
import org.apache.hadoop.io.IOUtils;
import org.apache.hadoop.io.compress.CompressionCodec;
import org.apache.hadoop.io.compress.CompressionCodecFactory;
import org.apache.hadoop.io.compress.CompressionInputStream;
import org.apache.hadoop.io.compress.CompressionOutputStream;
import org.apache.hadoop.util.ReflectionUtils;

import java.io.*;

public class TestCompress {
    public static void main(String[] args) throws IOException, ClassNotFoundException {
        //compress("G:\\Fly Away-梁靜茹.mp3", "org.apache.hadoop.io.compress.GzipCodec");
        deCompress("G:\\Fly Away-梁靜茹.mp3.gz", "mp3");

    }

//壓縮
    public static void compress(String filename, String method) throws IOException, ClassNotFoundException {
        //創(chuàng)建輸入流
        FileInputStream fis = new FileInputStream(new File(filename));

        //通過(guò)反射獲取壓縮類的Class 對(duì)象
        Class codecClass = Class.forName(method);

        //通過(guò)反射獲取壓縮對(duì)象
        CompressionCodec codec = (CompressionCodec)ReflectionUtils.newInstance(codecClass, new Configuration());

        //創(chuàng)建普通輸出流對(duì)象
        FileOutputStream fos = new FileOutputStream(new File(filename + codec.getDefaultExtension()));

        //通過(guò)壓縮對(duì)象創(chuàng)建壓縮輸出流,類似于將普通輸出流封裝成壓縮輸出流
        CompressionOutputStream cos = codec.createOutputStream(fos);

        //流拷貝
        IOUtils.copyBytes(fis, cos, 1024 * 1024 * 5, false);

        fis.close();
        cos.close();
        fos.close();

    }

//解壓
    public static void deCompress(String filename, String decode) throws IOException {
        CompressionCodecFactory factory = new CompressionCodecFactory(new Configuration());

        //獲取文件的壓縮算法類型對(duì)象,返回值可用于檢查文件是否可解壓
        CompressionCodec codec = factory.getCodec(new Path(filename));
        if (codec == null) {
            System.out.println("不支持解壓縮:" + filename);
            return;
        }

        //根據(jù)壓縮文件的壓縮類型,返回的對(duì)象用于創(chuàng)建壓縮輸入流
        CompressionInputStream cis = codec.createInputStream(new FileInputStream(new File(filename)));

        //創(chuàng)建輸出流
        FileOutputStream fos = new FileOutputStream(new File(filename + decode));

        IOUtils.copyBytes(cis, fos, 1024 * 1024 * 5, false);

        cis.close();
        fos.close();

    }
}

2、map輸出采用壓縮

用法很簡(jiǎn)單,只需在driver中給job配置以下參數(shù)即可

Configuration configuration = new Configuration();

// 開啟map端輸出壓縮
configuration.setBoolean("mapreduce.map.output.compress", true);
// 設(shè)置map端輸出壓縮方式
configuration.setClass("mapreduce.map.output.compress.codec", BZip2Codec.class, CompressionCodec.class);

3、reduce輸出采用壓縮

依舊是在driver中設(shè)置以下

// 設(shè)置reduce端輸出壓縮開啟
FileOutputFormat.setCompressOutput(job, true);

// 設(shè)置壓縮的方式
FileOutputFormat.setOutputCompressorClass(job, BZip2Codec.class); 
//      FileOutputFormat.setOutputCompressorClass(job, GzipCodec.class); 
//      FileOutputFormat.setOutputCompressorClass(job, DefaultCodec.class); 
向AI問(wèn)一下細(xì)節(jié)

免責(zé)聲明:本站發(fā)布的內(nèi)容(圖片、視頻和文字)以原創(chuàng)、轉(zhuǎn)載和分享為主,文章觀點(diǎn)不代表本網(wǎng)站立場(chǎng),如果涉及侵權(quán)請(qǐng)聯(lián)系站長(zhǎng)郵箱:is@yisu.com進(jìn)行舉報(bào),并提供相關(guān)證據(jù),一經(jīng)查實(shí),將立刻刪除涉嫌侵權(quán)內(nèi)容。

AI