Hadoop對於壓縮文件的支持及算法優缺點

Hadoop對於壓縮格式的是透明識別,我們的MapReduce任務的執行是透明的,hadoop能夠自動爲我們 將壓縮的文件解壓,而不用我們去關心。

  如果我們壓縮的文件有相應壓縮格式的擴展名(比如lzo,gz,bzip2等),hadoop就會根據擴展名去選擇解碼器解壓。

壓縮格式 工具 算法 文件擴展名 多文件 可分割性
DEFLATE 無 DEFLATE .deflate 不 不
gzip gzip DEFLATE .gz 不 不
ZIP zip DEFLATE .zip 是 是,在文件範圍內
bzip2 bzip2 bzip2 .bz2 不 是
LZO lzop LZO .lzo 不 是

         如果壓縮的文件沒有擴展名,則需 要在執行mapreduce任務的時候指定輸入格式.

hadoop jar /usr/home/hadoop/hadoop-0.20.2/contrib/streaming/hadoop-streaming-0.20.2-CD H3B4.jar -
file /usr/home/hadoop/hello/mapper.py -
mapper /usr/home/hadoop/hello/mapper.py -
file /usr/home/hadoop/hello/reducer.py -
reducer /usr/home/hadoop/hello/reducer.py -input lzotest -output result4 -jobconf mapred.reduce.tasks=1 *-inputformat org.apache.hadoop.mapred.LzoTextInputFormat*
  hadoop下各種壓縮算法的壓縮比,壓縮時間,解壓時間見下表:

壓縮算法 原始文件大小 壓縮後的文件大小 壓縮速度 解壓縮速度
gzip   8.3GB   1.8GB 17.5MB/s 58MB/s
bzip2 8.3GB 1.1GB 2.4MB/s 9.5MB/s
LZO-bset 8.3GB 2GB 4MB/s 60.6MB/s
LZO 8.3GB 2.9GB 49.3MB/S 74.6MB/s

  hadoop各種壓縮算法的優缺點簡述

  在考慮如何壓縮那些將由MapReduce處理的數據時,考慮壓縮格式是否支持分割是很重要的。考慮存儲在HDFS中的未壓縮的文件,其大小爲1GB,HDFS的塊大小爲64MB,所以該文件將被存儲爲16塊,將此文件用作輸入的MapReduce作業會創建1個輸人分片(split ,也稱爲“分塊”。對於block,我們統一稱爲“塊”。)每個分片都被作爲一個獨立map任務的輸入單獨進行處理。

  現在假設。該文件是一個gzip格式的壓縮文件,壓縮後的大小爲1GB。和前面一樣,HDFS將此文件存儲爲16塊。然而,針對每一塊創建一個分塊是沒有用的,因爲不可能從gzip數據流中的任意點開始讀取,map任務也不可能獨立於其他分塊只讀取一個分塊中的數據。gzip格式使用DEFLATE來存儲壓縮過的數據,DEFLATE將數據作爲一系列壓縮過的塊進行存儲。問題是,每塊的開始沒有指定用戶在數據流中任意點定位到下一個塊的起始位置,而是其自身與數據流同步。因此,gzip不支持分割(塊)機制。

  在這種情況下,MapReduce不分割gzip格式的文件,因爲它知道輸入是gzip壓縮格式的(通過文件擴展名得知),而gzip壓縮機制不支持分割機制。這樣是以犧牲本地化爲代價:一個map任務將處理16個HDFS塊。大都不是map的本地數據。與此同時,因爲map任務少,所以作業分割的粒度不夠細,從而導致運行時間變長。

  在我們假設的例子中,如果是一個LZO格式的文件,我們會碰到同樣的問題,因爲基本壓縮格式不爲reader提供方法使其與流同步。但是,bzip2格式的壓縮文件確實提供了塊與塊之間的同步標記(一個48位的PI近似值),因此它支持分割機制。

  對於文件的收集,這些問題會稍有不同。ZIP是存檔格式,因此它可以將多個文件合併爲一個ZIP文件。每個文件單獨壓縮,所有文檔的存儲位置存儲在ZIP文件的尾部。這個屬性表明ZIP文件支持文件邊界處分割,每個分片中包括ZIP壓縮文件中的一個或多個文件。

  在MapReduce我們應該使用哪種壓縮格式

  根據應用的具體情況來決定應該使用哪種壓縮格式。就個人而言,更趨向於使用最快的速度壓縮,還是使用最優的空間壓縮?一般來說,應該嘗試不同的策略,並用具有代表性的數據集進行測試,從而找到最佳方法。對於那些大型的、沒有邊界的文件,如日誌文件,有以下選項。

  存儲未壓縮的文件。

  使用支持分割機制的壓縮格式,如bzip2。

  在應用中將文件分割成幾個大的數據塊,然後使用任何一種支持的壓縮格式單獨壓縮每個數據塊(可不用考慮壓縮格式是否支持分割)。在這裏,需要選擇數據塊的大小使壓縮後的數據塊在大小上相當於HDFS的塊。

  使用支持壓縮和分割的Sequence File(序列文件)。

  對於大型文件,不要對整個文件使用不支持分割的壓縮格式,因爲這樣會損失本地性優勢,從而使降低MapReduce應用的性能。

  hadoop支持Splittable壓縮lzo

  在hadoop中使用lzo的壓縮算法可以減小數據的大小和數據的磁盤讀寫時間,在HDFS中存儲壓縮數據,可以使集羣能保存更多的數據,延長集羣的使用壽命。不僅如此,由於mapreduce作業通常瓶頸都在IO上,存儲壓縮數據就意味這更少的IO操作,job運行更加的高效。

  但是在hadoop上使用壓縮也有兩個比較麻煩的地方:第一,有些壓縮格式不能被分塊,並行的處理,比如gzip。第二,另外的一些壓縮格式雖然支持分塊處理,但是解壓的過程非常的緩慢,使job的瓶頸轉移到了cpu上,例如bzip2。


轉載地址:http://www.linuxidc.com/Linux/2012-05/60553.htm

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章