• 标记清除法

标记清除算法,是将垃圾回收分为2个阶段,分别是标记和清除

  • 标记:从根节点开始标记引用的对象。
  • 清除:未被标记引用的对象就是垃圾对象,可以被清理。

原理

Java删除 vo对象的某个属性 jvm删除对象_内存空间

这张图代表的是程序运行期间所有对象的状态,他们的标志位全部是0(也就是未标记,以下默认0就是未标记,1为已标记),假设这会儿有效内存空间耗尽了,JVM将会停止应用程序的运行并开启GC线程,然后开始进行标记工作,按照根搜索算法,标记玩以后,对象的状态如下图。

Java删除 vo对象的某个属性 jvm删除对象_内存空间_02

可以看到,按照根搜索算法,所有从root对象可达的对象就被标  记为了存活的对象,此时已经完成了第一阶段标记。接下来,就要执行第二阶段清除了,那么清除完之后,剩下的对象以及对象的状态如下图所示。

Java删除 vo对象的某个属性 jvm删除对象_搜索算法_03

可以看到,没有被标记的对象将会回收清除掉,而被标记的对象将会留下,并且会将标记位重新归0.接下来就不用了说了,幻想停止的程序线程,让程序继续运行即可

优缺点:

可以看到标记清除算法解决了引用计数法中的循环引用的问题,没有从root节点引用的对象都会被回收。

同样,标记清除算法也是有缺点的:

  • 效率较低,标记和清除两个动作都需要遍历所有的对象,并且在GC时,需要停止应用程序,对于交互性要求比较高的应用而言这个体验是非常差的。
  • 通过标记清除算法清理出来的内存,碎片化较为严重,因为被回收的对象可能存在于内存的各个角落,所有清理出来的内存是不连贯的。