- 主要針對堆內存回收算法
1. 都有哪些GC回收算法 ?多線程
Ø 三個問題併發
² 哪些對象能夠回收?性能
² 如何回收?優化
² 何時回收?ui
Ø 解決哪些對象能夠回收 ?spa
1) 引用計數器 比較老的算法線程
原理:對象引用過一次,標記+1;減小一次引用,標記-1;長時間不用,到標記爲0的時候 回收對象
問題:很難解決對象循環引用的問題,就是兩個對象相互引用,一致清除不掉內存
2)可達性分析算法 經常使用的算法
原理:和GCRoot有關係,留着;沒有關係清除;通常只有棧對象,靜態變量對象,常量能夠當GCRoot.
Ø 解決如何回收?
1) 標記- 清除
問題:會產生大量不連續的內存碎片,大文件存不了,怎麼辦?在收集一次,還存不了,怎麼辦?
虛擬內存機制, 將一部分文件存到磁盤IO上;可是不用,影響性能
2) Copying算法
堆內存分紅兩份,一份塊爲不可清除狀態,一塊爲可清除狀態,1:1的關係,收集內存中的新生代
問題:內存使用率低
改進:1塊大的Eden和兩塊較小的Suivior空間,新建立的放在Eden中;
清除的時候能清除的清除,不能清除的放到Suivivor中,(8:1) 主流使用;
Cpoying算法的改進對提升了內存管理的效率。
新生代存不下,常常存活,把一部分數據存放到老年代.
3) 標記-整理算法
老生代不多發生GC,都是常常用的對象;用在老生帶。
內存滿以後,將一些不用的,標記移到一塊,在刪除,不會產生內存碎片
4) 分代收集算法:
將整個堆分紅新生代,和老生代,
Ø 誰來回收?
垃圾回收器來回收垃圾
有哪些垃圾回收器?
- 新生代
copying算法
全部的代一直在 革新,可是並無徹底替代
第一代Serial:
Jdk1.3版本,單線程收集器,其它全部線程就要停掉等它完成工做
這個現象不能消除,後續的就是不斷優化減小時間的過程
佔用內存小的時候使用它是很好的,能提升效率。
第二代:ParNew
Serial的多線程版本
併發收集器,垃圾線程和用戶線程同時工做
第三代:Parallel Scavenge收集器
能夠達到一個可控制的吞吐量,吞吐量優先收集器
頻繁和用戶交互的程序不使用
Spark默認用的就是該款收集器,能夠在該配置文件中調整 spark-defaults.conf,收集器之間能夠組合
- 老年代
Parallel Old,
CMS收集器
以獲取最短回收停頓時間爲目標的收集器,具於「標記-清除」算法實現
有叫 併發停頓收集器
初始標記 只標記GCroot能關聯到的對象,速度很快,用戶線程會停頓
併發標記 併發標記階段,用戶線程不會停頓
從新標記 修正併發階段產生的變化
併發清除 用戶線程和垃圾線程同時工做,用戶線程不會停頓
和用戶交互場景多建議使用,
存在問題:對Cpu的資源很是敏感,沒法處理浮動垃圾
所以須要留出一部分空間給浮動垃圾使用,這一部分默認小於10%。
會產生大量內存碎片。
Ø GC算髮!
在傳統JVM內存管理中,咱們把Heap空間分爲Young/Old兩個分區,Young分區又包括一個Eden和兩個Survivor分區,以下圖所示。新產生的對象首先會被存放在Eden區,而每次minor GC發生時,JVM一方面將Eden分區內存活的對象拷貝到一個空的Survivor分區,另外一方面將另外一個正在被使用的Survivor分區中的存活對象也拷貝到空的Survivor分區內。
在此過程當中,JVM始終保持一個Survivor分區處於全空的狀態。一個對象在兩個Survivor之間的拷貝到必定次數後,若是仍是存活的,就將其拷入Old分區。當Old分區沒有足夠空間時,GC會停下全部程序線程,進行Full GC,即對Old區中的對象進行整理。注意:Full GC時,全部線程都暫停,因此這個階段被稱爲Stop-The-World(STW),也是大多數GC算法中對性能影響最大的部分。
2. Sparc 內存管理GI回收算法 ?
而G1 GC則徹底改變了這一傳統思路。它將整個Heap分爲若干個預先設定的小區域塊,每一個區域塊內部再也不進行新舊分區, 而是將整個區域塊標記爲Eden/Survivor/Old。當建立新對象時,它首先被存放到某一個可用區塊(Region)中。當該區塊滿了,JVM就會建立新的區塊存放對象。當發生minor GC時,JVM將一個或幾個區塊中存活的對象拷貝到一個新的區塊中,並在空餘的空間中選擇幾個全新區塊做爲新的Eden分區。當全部區域中都有存活對象,找不到全空區塊時,才發生Full GC。而在標記存活對象時,G1使用RememberSet的概念,將每一個分區外指向分區內的引用記錄在該分區的RememberSet中,避免了對整個Heap的掃描,使得各個分區的GC更加獨立。
在這樣的背景下,咱們能夠看出G1 GC大大提升了觸發Full GC時的Heap佔用率,同時也使得Minor GC的暫停時間更加可控,對於內存較大的環境很是友好
關於Hotspot JVM所支持的完整的GC參數列表,能夠參見Oracle官方的文檔中對部分參數的解釋。