? 從事java行業開始,對垃圾回收器是又熟悉又陌生,當面試的時候或者工作的時候,對垃圾回收期又非常的敬畏,如今,終于對這玩意有點了解了。
? ? 一、垃圾回收器分為新生代,老生代,持久代。
? ? ? 新生代有eden區,二個 survivor區。new一個對象,則在堆內存存放了一個對象,也就是存放在新生代(eden),當對象通過根搜索算法判定為不可達,再通過二次標記為待回收時,則等待下次gc回收了,當eden內存滿了,會進行GC,通過標記復制算法,把仍存活的對象復制到suvor區的其中一個區(from survivor),同時eden清除清空,當from survevor滿了,同樣的回收算法,就會把eden,from survivor區仍存活的對象復制到另一個survivor(to survivor),同時eden,from survivor清空,如果大對象在to survivor存放不了,則會還復制進老生區。老生區滿的時候,則通過標記整理或者分代收集算法(!)進行回收,進行full gc。當jvm進行full gc的時候,會造成線程堵塞,cpu暴漲,所以減少full gc。另外特別注意,大對象會直接進去老生區,存活年齡大的對象也會直接進去老生區。
二、垃圾回收算法
在上面提過,各個分區在垃圾回收時候,執行的算法。可以歸結為,在eden,新生對象比較頻繁,所以采用標記清除算法,在survivor區則采用的是復制算法,在老生區用的是標記整理算法,現在生產環境的算法用的都是分代收集算法。簡單說一下分代收集算法,是區分新生代和老生代執行不行的算法,比如新生代eden則執行標記清除,survivor則執行復制算法,老生區則執行標記整理算法。下面來說一下各算法的區別,標記清除算法,比較耗內存效率低,復制算法則避免了。老生區為了更快的效率不用來回復制,直接將待回收的放到一個邊緣,超過的被執行回收。