jvm的垃圾回收机制

一 谈一谈jvm的垃圾回收机制

1.1 什么是垃圾回收
  在正式介绍垃圾回收算法前,先来说说什么是垃圾回收。这里所说的垃圾主要指的是已经不会再继续使用的对象,当然也有可能是其他,比如不再使用的类以及常量,但主要还是指对象,所以以下算法将介绍对象的回收。所以垃圾回收的含义就是:将内存中已经不会被使用的对象(或类和常量)清除,释放内存空间。

JVM的内存模型分为五个部分,其中堆内存的唯一目的就是存放对象,对象也基本上都是存放在堆内存中。堆中,为了方便进行垃圾回收,一般会将内存分为两个部分:

老年代:用来存放生命周期长的对象。新生代中存活了较长时间的对象会被迁移到这里(当然,对象进入老年代不仅仅只有这一个方法),所以这里存放的对象生命周期一般较长,所以这一块区域发生垃圾回收的频率较低,释放的空间也较少;
新生代:用来存放生命周期短的对象。由于这一块内存中的对象存活时间较短,所以频繁发生垃圾回收,而且每次回收一般都能释放大量空间;

下面正式开始讨论JVM中的垃圾回收算法。

1.2 识别垃圾的方式
(1) 引用计数法
引用计数法就是通过引用来识别无用对象。我们记录每一个对象的引用个数,若有新的变量引用一个对象时,这个对象的引用个数加1;若一个引用失效时,引用的个数减1,而引用个数为0的对象,即可作为垃圾被回收。这里要注意,若这些垃圾对象的成员变量引用了其他对象,则当垃圾对象被释放时,它的这个引用自然就失效了。

这个算法实现简单,效率也高,但是,它并没有被用在主流的Java虚拟机中,因为它有一个很大的缺陷——很难解决循环引用的问题
(2)可达性分析法
   可达性分析法是Java垃圾回收中判别无用对象的主要方法。这个方法的步骤是,从根节点对象出发,使用DFSBFS算法,沿着引用递归遍历,而无法被遍历到的对象,就是无法再被使用的对象,可以被垃圾回收器回收。所谓的根节点,就是我们能够直接使用的引用类型变量,如:

1)方法中的参数或局部变量;
2)类的静态成员或非静态成员;
3)代码中的常量;
  这种方法的效率相对于引用计数来说相对复杂,而且效率较低,但是解决了循环引用的问题,是Java垃圾回收中主要使用的方法。
  关于可达性分析可以看一看这位大佬写的:java可达性分析详解
1.3 如何释放垃圾
  释放垃圾指的就是清除无用对象,释放它们所占的内存空间,方便继续使用。这里主要介绍三种方法:

1:标记—清除算法
2:复制算法;
3:标记—整理算法;

  这三种算法根据具体情况的不同,搭配使用,才能发挥最好的效果。这些东西我收集了比较好的解答。
  标记-清除算法推荐阅读:  
  复制算法具体解析;
  标记—整理算法;

4分代收集算法
分代收集算法并不是什么新思想,而是对上面三种算法的综合使用。前面也提过,为方便垃圾回收,一般将堆内存分为新生代和老年代两个部分。

对于新生代而言,这一块区域中的对象存活时间短,每一次垃圾回收都能回收大部分内存,所以适合使用复制算法,同时以老年代作为这个算法的担保空间;
对于老年代而言,每次垃圾回收只能释放小部分空间,若使用复制算法,每次将需要做大量复制,而且此时Survivor需要较大的空间,所以不适合使用复制算法,因此在老年代中,一般使用标记—清除或者标记—整理算法;
讲解的比较清除:深入理解JVM------分代收集算法
1.3 完结
以上就是java垃圾回收机制流程.

你可能感兴趣的:(java,jvm,算法,编程语言)