Spark內存管理

一、spark的一大特性就是基於內存計算,Driver只保存任務的宏觀性的元數據,數據量較小,且在執行過程當中基本不變,不作重點分析,而真正的計算任務Task分佈在各個Executor中,其中的內存數據量大,且會隨着計算的進行會發生實時變化,因此Executor的內存管理才分析的重點。

二、在執行Spark應用程序時,集羣會啓動Driver和Executor兩種JVM進程,前者爲主控進程,負責建立spark上下文(context),提交spark做業(job),將做業轉化爲計算任務(task),在各個Executor進程間協調任務的調度。後者負責在工做節點上執行具體任務,並將結果返回給Driver,同時爲須要持久化的RDD提供存儲功能。

三、做爲一個JVM進程,Executor的內存管理時基於JVM內存管理機制的,spark對JVM-on-heap內存進行了更爲詳細的規劃,以充分利用。同時spark還引入了off-heap內存,使之能夠直接從運行節點的系統內存中開闢空間,進一步優化內存的使用。
【堆內存的分配和回收徹底依賴JVM的gc機制,應用不能靈活的操做內存,使用堆外內存則能夠經過OS來分配和釋放,較爲靈活】

早期靜態內存管理:on-heap分爲四個區域,分別是Storage(20%)、Execution(60%)、Other(20%)、Ext,Storage用於緩存持久化的RDD數據和廣播變量等,Execution用於緩存shuffle過程當中產生的中間數據,Other區用於存儲運行中的其餘對象,Ext是一塊較小的預留空間,用以防止OOM的發生,起到兜底做用,幾個區塊間有嚴格的界限,不可逾越。off-heap分爲兩個區,Storage(50%)、Execution(50%),也有嚴格界限,不可逾越。
spark1.6後引入統一內存管理:與靜態管理機制的不一樣在於初始Storage(50%)、Execution(50%),在執行過程當中兩個區域能夠根據本身和對方的內粗餘量彈性的越界分配,更加靈活高效。off-heap也是兩個區域,沒有嚴格界限能夠動態佔用。

四、內存的動態佔用:
0.存儲 < 50% && 執行 < 50%:互不佔用
1.存儲 > 50% && 執行 > 50%:溢寫磁盤(前提是緩存級別包含磁盤,若級別爲純內存則丟棄數據)
2.存儲 > 50% && 執行 < 50%:存儲跨界借用,若一段時間後執行內存不足,則刪除被借用內存,優先知足執行的內存須要。
3.存儲 < 50% && 執行 > 50%:執行跨界借用,若一段時間後存儲內存不足,則不能被執行佔用的存儲區內存,由於執行的優先級更高,要優先保證執行數據。
***
五、統一內存管理機制,有效的提升了堆內存和堆外內存的使用效率,下降了使用複雜度,可是並不能就此高枕無憂。因爲RDD數據每每是長期生存的,若是存儲在內存中的數據過多,會引起頻繁的full-gc,下降了程序的吞吐量。緩存

相關文章
相關標籤/搜索