这是我参与11月更文挑战的第18天,活动详情查看:2021最后一次更文挑战
前言
在上一篇章我们讲了垃圾回收的垃圾是如何定义的,本章重点讲述垃圾的三种死法。
标记-清除
标记要被清理的对象,然后把未被标记的对象清除。反之,也可以标记为被清理的对象,把标记的对象清除。两者取决于垃圾收集器如何实现。标记垃圾的算法也就是可达性算法,不了解的可以看我上一篇章。标记清除的算法是以下两种算法的基础部分,这个算法有个缺点就是如果对象越多,那么清除起来越满,并且清除后会产生大量的内存碎片,导致空间不连续,其带来的后果就是你有一个2k的对象,但是你的内存第一个部分1k第二个部分有对象第三个部分1k,你是不可以拆分放在这个1k+1k的,你只能等待下次连续对象来放入。
标记-复制
标记复制是同样会标记起来,然后对标记的对象进行移动,把标记的对象放入另一篇内存空间,内存空间也要一分为二,一片为空的,一片为存放对象的,在放入另一片的时候会保证内存的连续性,这样的好处就是不会产生内存碎片了。但同时也占用了两片内存空间。
标记-整理
标记整理也是基于标记清除算法而来。他则是标记需要清理的对象,然后把未被标记的对象清除,紧接着再把对象进行移动,目的是为了把内存碎片清理掉,但是这个过程非常的耗时。但好处就是没有内存碎片。
GC划分
在之前的运行时数据区篇章我们讲过,堆基于分代假说理论被分为了两个部分,第一个部分为年轻代,第二个部分为老年代。
Minor GC
年轻代的对象基本都是遵循朝生夕灭的规律来生存,但是如果这对象可以活很久,对象一旦占满年轻代的eden区,那么就会触发轻GC也就是Minor GC。轻GC触发它会采用标记-复制算法,并且由于是和用户线程一起运行,当GC触发会触发STW,停止世界事件。也就是把用户线程停止,全力运行GC线程,但是轻GC一般停顿很短,让人感受不到STW。
Major GC
老年代的对象会存活非常久,但是老年代满了他的GC会比较严重,他会触发FUll GC也就是老年代 + 新生代都要GC,这会带来STW,并且是长时间的STW,老年代采用了标记-整理算法,这个算法的停顿时间很长。