mapreduce優化總結


集群的優化

1、合理分配map和reduce任務的數量(單個節點上map任務、reduce任務的最大數量)

2、其他配置

io.file.buffer.size

hadoop訪問文件的IO操作都需要通過代碼庫。因此,在很多情況下,io.file.buffer.size都被用來設置緩存的大小不論是對硬盤或者是網絡操作來講,較大的緩存都可以提供更高的數據傳輸,但這也就意味着更大的內存消耗和延遲

這個參數要設置為系統頁面大小的倍數,以byte為單位,默認值是4KB,一般情況下,可以設置為64KB(65536byte)

dfs.balance.bandwidthPerSec

HDFS平衡器檢測集群中使用過度或者使用不足的DataNode,並在這些DataNode之間移動數據塊來保證負載均衡,如果不對平衡操作進行帶寬限制,那么它會很快就會搶占所有的網絡資源,不會為Mapreduce作業或者數據輸入預留資源

參數dfs.balance.bandwidthPerSec定義了每個DataNode平衡操作所允許的最大使用帶寬,這個值的單位是byte,這是很不直觀的,因為網絡帶寬一般都是用bit來描述的。因此,在設置的時候,要先計算好。DataNode使用這個參數來控制網絡帶寬的使用,但不幸的是,這個參數在守護進程啟動的時候就讀入,導致管理員沒辦法在平衡運行時來修改這個值

dfs.block.size    默認128M

dfs.block.size的單位是byte,默認值是67108864 (64MB)。對於很多情況來說,134217728 (128MB)更加合適

對於一個Mapreduce作業(尤其是用子類FileInputFormat定義輸入格式的作業),對文件的每個數據塊會啟用一個map任務來處理

這就意味這數據塊的大小顯著地影響Mapreduce作業的效率

dfs.datanode.du.reserved 保留空間  用於mapreduce使用 默認為0

當DataNode向NameNode匯報可用的硬盤大小的時候,它會把所有dfs.data.dir所列出的可用的硬盤大小總和發給NameNode

由於mapred.local.dir經常會跟DataNode共享可用的硬盤資源,因為我們需要為Mapreduce任務保留一些硬盤資源。dfs.datanode.du.reserved

定義了每個dfs.data.dir所定義的硬盤空間需要保留的大小,以byte為單位。默認情況下,該值為0.也就意味着HDFS可以使用每個數據硬盤的所有空間

節點硬盤資源耗盡時就會進入讀模式。因此,建議每個硬盤都為map任務保留最少10GB的空間,如果每個Mapreduce作業都會產生大量的中間結果

或者每個硬盤空間都比較大(超過2TB),那么建議相應的增大保留的硬盤空間

dfs.namenode.handler.count       

NameNode有一個工作線程池用來處理客戶端的遠程過程調用及集群守護進程的調用。處理程序數量越多意味着要更大的池來處理來自不同DataNode的並發心跳以及客戶端並發的元數據操作。對於大集群或者有大量客戶端的集群來說,通常需要增大參數dfs.namenode.handler.count的默認值10。設置該值的一般原則是將其設置為集群大小的自然對數乘以20,即20logN,N為集群大小

如果該值設的太小,明顯的狀況就是DataNode在連接NameNode的時候總是超時或者連接被拒絕,但NameNode的遠程過程調用隊列很大時遠程過程調用延時就會加大。症狀之間是相互影響的,很難說修改dfs.namenode.handler.count就能解決問題,但是在查找故障時,檢查一下該值的設置是必要的

dfs.datanode.failed.volumes.tolerated

當DataNode的任何一個本地磁盤出故障時,它的默認行為認定整個DataNode失效。在一個中到大型的集群中,硬盤故障是相當常見的,所以這種行為不是最優的。一個 DataNode的丟失會導致一些數據塊備份數下降,因此,NameNode會命令其他DataNode復制這些丟失的數據塊來增加被附屬。參數dfs.datanode.failed.volumes.tolerated 定義整個DataNode聲明失敗前允許多少個硬盤出現故障

很多人會問,為什么不能容忍所有磁盤失效的情況,這樣就可以把整個DataNode的失效推遲到沒有任何可工作的硬盤為止

對於一個永久的時間窗口來說,這看上去很合理的,但是實際上,對於所以的磁盤來說,管理員對於磁盤故障的處理都會早於由於正常磨損而出現的故障。只有一種情況例外,所以的硬盤在一個極短的時間內全部出現故障,這種異常情況需要立即調查。在實踐中快速的磁盤故障通常意味着驅動控制器或者某些部件故障。正因為罕見,但如果磁盤在短時間內開始出現一連串故障,最好的辦法就是立即隔離。先把整個集群設置為不可用,直到找到失敗的原因為止。參數dfs.datanode.failed.volumes.tolerated默認值為0,也就意味着只要有一個磁盤出現故障就會導致整個DataNode不可用,管理員可以增大該值來保證在出現部分磁盤故障時,DataNode仍能持續運行,但是需要保持謹慎的是,在極短的時間范圍內出現一個或者兩個磁盤故障表明一個更大的問題存在

fs.trash.interval

   用戶經常會意外刪除文件。HDFS支持回收站功能,這類似於大多數操作系統的回收站,當這個功能被啟用文件被移到用戶的HDFS主目錄中一個名為.Trash目錄中,來保留被刪除的文件,而不是立即徹底刪除。fs.trash.interval定義.Trash目錄下文件被永久刪除前保留的時間。在文件被從HDFS永久刪除前,用戶可以自由地把文件從該目錄下移出來並立即還原。默認值是0說明垃圾回收站功能是關閉的。要清楚,回收站功能不是萬能的,推遲刪除意味着要文件所占據的空間仍不可用,除非它被永久刪除。用戶可以通過運行hadoop fs -expunge命令。或者干脆等待指定的時間來明確回收站清空。可以在hadoop fs -rm命令通過指定-skipTrash參數來跳過回收站從而立即刪除文件

3、map的優化

io.sort.mb  默認為100M

map任務產生中間數據默認會先放到內存中 當大小達到上面設置的值會進行spill根據需要調整改參數  適當增大 減少spill的次數

io.sort.spill.percent  一般不做調整

spill時占比 默認為0.8

io.sort.factor   默認為10

在map任務計算完成后會有一個merge操作 默認為10  即最多10個spill文件合並,如果spill大於10個會分多次merge,合理的設置該參數可以減少merge次數

min.num.spill.for.combine(default 3)

當job中設定了combiner,並且spill數最少有3個的時候,那么combiner函數就會在merge產生結果文件之前運行

如果spill過多的時候 合適的設置該值 可以減少spill前的數據,減少合並時的數據

mapred.compress.map.output(default false)

也就是說map的中間,無論是spill的時候,還是最后merge產生的結果文件,都是可以壓縮的

壓縮的好處在於,通過壓縮減少寫入讀出磁盤的數據量,中間結果非常大,磁盤速度成為map執行瓶頸的job,尤其有用

該參數采用的是cpu換io(解壓縮) ,一般來說都會是磁盤io產生瓶頸 ,所以通常可以設置為true

mapred.map.output.compression.codec( default org.apache.hadoop.io.compress.DefaultCodec)

采用map中間結果壓縮的情況下,用戶還可以選擇壓縮時采用哪種壓縮格式進行壓縮

現在hadoop支持的壓縮格式有:GzipCodec,LzoCodec,BZip2Codec,LzmaCodec等壓縮格式

通常來說,想要達到比較平衡的cpu和磁盤壓縮比,LzoCodec比較適合。但也要取決於job的具體情況

4、reduce的優化

reduce  分成三個階段的 分別為copy->sort->reduce

由於job的每一個map都會根據reduce(n)數將數據分成map 輸出結果分成n個partition,所以map的中間結果中是有可能包含每一個reduce需要處理的部分數據的,所以,為了優化reduce的執行時間,hadoop中是等job的第一個map結束后,所有的reduce就開始嘗試從完成的map中下載該reduce對應的partition部分數據,這個過程就是通常所說的shuffle,也就是copy過程

mapred.reduce.parallel.copies(default 5)  每個reduce並行下載map結果的最大線程數

每個只會有5個並行的下載線程在從map下數據,如果一個時間段內job完成的map有100個或者更多,那么reduce也最多只能同時下載5個map的數據

所以這個參數比較適合map很多並且完成的比較快的job的情況下調大,有利於reduce更快的獲取屬於自己部分的數據

mapred.reduce.copy.backoff(default 300秒)  reduce下載線程最大等待時間(秒)

reduce的每一個下載線程在下載某個map數據的時候,有可能因為那個map中間結果所在機器發生錯誤或者中間結果的文件丟失,或者網絡瞬斷等等情況,這樣reduce的下載就有可能失敗,所以reduce的下載線程並不會無休止的等待下去,當一定時間后下載仍然失敗,那么下載線程就會放棄這次下載,並在隨后嘗試從另外的地方下載,如果集群環境的網絡本身是瓶頸,那么用戶可以通過調大這個參數來避免reduce下載線程被誤判為失敗的情況。不過在網絡環境比較好的情況下,沒有必要調整。通常來說專業的集群網絡不應該有太大問題,所以這個參數需要調整的情況不多

io.sort.factor

Reduce將map結果下載到本地時,同樣也是需要進行merge的,所以io.sort.factor的配置選項同樣會影響reduce

進行merge時的行為,當發現reduce在shuffle階段iowait非常的高的時候,就有可能通過調大這個參數來加大一次merge時

的並發吞吐,優化reduce效率

mapred.job.shuffle.input.buffer.percent(default 0.7)  用來緩存shuffle數據的reduce task heap百分比

Reduce在shuffle階段對下載來的map數據,並不是立刻就寫入磁盤的,而是會先緩存在內存中,然后當使用內存達到一定量的時候才刷入磁盤,這個內存大小的控制就不像map一樣可以通過io.sort.mb來設定了,而是通過另外一個參數來設置,也就是說,如這個參數其實是一個百分比,意思是說,shuffile在reduce內存中的數據最多使用內存量為:0.7 × maxHeap of reduce task果該reduce task的最大heap使用量(通常通過mapred.child.java.opts來設置,比如設置為-Xmx1024m)的一定比例用來緩存數據,如果reduce的heap由於業務原因調整的比較大,相應的緩存大小也會變大,這也是為什么reduce用來做緩存的參數是一個百分比,而不是一個固定的值了

mapred.job.shuffle.merge.percent(default 0.66)  緩存的內存中多少百分比后開始做spill操作

如果下載速度很快,很容易就把內存緩存撐大,那么調整一下這個參數有可能會對reduce的性能有所幫助

mapred.job.reduce.input.buffer.percent(default 0.0)  sort完成后reduce計算階段用來緩解數據的百分比

當reduce將所有的map上對應自己partition的數據下載完成后,就會開始真正的reduce計算階段(中間有個sort階段通常時間非常短,幾秒鍾就完成了,因為整個下載階段就已經是邊下載邊sort,然后邊merge的)當reduce task真正進入reduce函數的計算階段的時候,有一個參數也是可以調整reduce的計算行為,由於reduce計算時肯定也是需要消耗內存的,而在讀取reduce需要的數據時,同樣是需要內存作為buffer,這個參數是控制,需要多少的內存百分比來作為reduce讀已經sort好的數據的buffer百分比,默認情況下為0也就是說,默認情況下,reduce是全部從磁盤開始讀處理數據,如果這個參數大於0,那么就會有一定量的數據,被緩存在內存並輸送給reduce,當reduce計算邏輯消耗內存很小時,可以分一部分內存用來緩存數據,反正reduce的內存閑着也是閑着

mapred.reduce.slowstart.completed.maps(map完成多少百分比時,開始shuffle)

當map運行慢,reduce運行很快時,如果不設置mapred.reduce.slowstart.completed.maps會使job的shuffle時間變的很長,map運行完很早就開始了reduce,導致reduce的slot一直處於被占用狀態,這個值是和“運行完的map數除以總map數”做判斷的,當后者大於等於設定的值時,開始reduce的shuffle。所以當map比reduce的執行時間多很多時,可以調整這個值(0.75,0.80,0.85及以上)

下面從map流程里描述一下map中各個參數的作用:  沒有reduce

1、當map task開始運算,並產生中間數據時,其產生的中間結果並非直接就簡單的寫入磁盤。這中間的過程比較復雜,並且利用到了

內存buffer來進行已經產生的部分結果的緩存,並在內存buffer中進行一些預排序來優化整個map的性能。每一個map都會對應存

在一個內存buffer(MapOutputBuffer),map會將已經產生的部分結果先寫入到該buffer中,這個buffer默認是100MB大小,但

是這個大小是可以根據job提交時的參數設定來調整的,該參數即為:io.sort.mb。當map的產生數據非常大時,並且把io.sort.mb

調大,那么map在整個計算過程中spill的次數就勢必會降低,map task對磁盤的操作就會變少,如果map tasks的瓶頸在磁盤上,

這樣調整就會大大提高map的計算性能

2、map在運行過程中,不停的向該buffer中寫入已有的計算結果,但是該buffer並不一定能將全部的map輸出緩存下來,當map輸出

超出一定閾值(比如100M),那么map就必須將該buffer中的數據寫入到磁盤中去,這個過程在mapreduce中叫做spill。map並

不是要等到將該buffer全部寫滿時才進行spill,因為如果全部寫滿了再去寫spill,勢必會造成map的計算部分等待buffer釋放空間的

情況。所以,map其實是當buffer被寫滿到一定程度(比如80%)時,就開始進行spill。這個閾值也是由一個job的配置參數來控

制,即io.sort.spill.percent,默認為0.80或80%。這個參數同樣也是影響spill頻繁程度,進而影響map task運行周期對磁盤的讀寫

頻率的。但非特殊情況下,通常不需要人為的調整。調整io.sort.mb對用戶來說更加方便。

3、當map task的計算部分全部完成后,如果map有輸出,就會生成一個或者多個spill文件,這些文件就是map的輸出結果。map在正

常退出之前,需要將這些spill合並(merge)成一個,所以map在結束之前還有一個merge的過程。merge的過程中,有一個參數

可以調整這個過程的行為,該參數為:io.sort.factor。該參數默認為10。它表示當merge spill文件時,最多能有多少並行的stream

向merge文件中寫入。比如如果map產生的數據非常的大,產生的spill文件大於10,而io.sort.factor使用的是默認的10,那么當

map計算完成做merge時,就沒有辦法一次將所有的spill文件merge成一個,而是會分多次,每次最多10個stream。這也就是說,

當map的中間結果非常大,調大io.sort.factor,有利於減少merge次數,進而減少map對磁盤的讀寫頻率,有可能達到優化作業的

目的

4、當job指定了combiner的時候,我們都知道map介紹后會在map端根據combiner定義的函數將map結果進行合並。運行combiner

函數的時機有可能會是merge完成之前,或者之后,這個時機可以由一個參數控制,即min.num.spill.for.combine(default 3),

當job中設定了combiner,並且spill數最少有3個的時候,那么combiner函數就會在merge產生結果文件之前運行。通過這樣的方

式,就可以在spill非常多需要merge,並且很多數據需要做conbine的時候,減少寫入到磁盤文件的數據數量,同樣是為了減少對磁

盤的讀寫頻率,有可能達到優化作業的目的

5、減少中間結果讀寫進出磁盤的方法不止這些,還有就是壓縮。也就是說map的中間,無論是spill的時候,還是最后merge產生的結

果文件,都是可以壓縮的。壓縮的好處在於,通過壓縮減少寫入讀出磁盤的數據量。對中間結果非常大,磁盤速度成為map執行瓶

頸的job,尤其有用。控制map中間結果是否使用壓縮的參數為:mapred.compress.map.output(true/false)。將這個參數設置為

true時,那么map在寫中間結果時,就會將數據壓縮后再寫入磁盤,讀結果時也會采用先解壓后讀取數據。這樣做的后果就是:寫

入磁盤的中間結果數據量會變少,但是cpu會消耗一些用來壓縮和解壓。所以這種方式通常適合job中間結果非常大,瓶頸不在

cpu,而是在磁盤的讀寫的情況。說的直白一些就是用cpu換IO。根據觀察,通常大部分的作業cpu都不是瓶頸,除非運算邏輯異常

復雜。所以對中間結果采用壓縮通常來說是有收益的

6、當采用map中間結果壓縮的情況下,用戶還可以選擇壓縮時采用哪種壓縮格式進行壓縮,現在hadoop支持的壓縮格式有:

GzipCodec,LzoCodec,BZip2Codec,LzmaCodec等壓縮格式。通常來說,想要達到比較平衡的cpu和磁盤壓縮比,LzoCodec

比較適合。但也要取決於job的具體情況。用戶若想要自行選擇中間結果的壓縮算法,可以設置配置參數:

mapred.map.output.compression.codec=org.apache.hadoop.io.compress.DefaultCodec或者其他用戶自行選擇的壓縮方式。


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM