JVM的GC垃圾回收机制

JVM会分配一个运行时内存空间。包括5大部分:程序计数器(Program Counter Register)、虚拟机栈(VM Stack)、本地方法栈(Native Method Stack)、方法区(Method Area)、堆(Heap)。其中程序计数器、虚拟机栈、本地方法栈是每个线程私有内存空间,随线程而生,随线程而亡。这3个区域内存分配和回收都是确定的,无需考虑内存回收的问题。
但方法区和堆就不同了,一个接口的多个实现类需要的内存可能不一样,只有在程序运行期间才会知道会创建哪些对象,这部分内存的分配和回收都是动态的,GC主要关注的是这部分内存。GC主要进行回收的内存是JVM中的方法区和堆,涉及到多线程(指堆)、多个对该对象不同类型的引用(指方法区),才会涉及GC的回收。
JVM GC怎么判断对象可以被回收了?

· 对象没有引用

· 作用域发生未捕获异常

· 程序在作用域正常执行完毕

· 程序执行了System.exit()

· 程序发生意外终止(被杀线程等)

Java GC怎么确定堆内存中哪些对象是存活的?
一般有两种方法:引用计数法和可达性分析法。

  • 引用计数:每个对象有一个引用计数属性,新增一个引用时计数加1,引用释放时计数减1,计数为0时可以回收。引用计数法实现简单,判定高效,但不能解决对象之间相互引用的问题。
  • 可达性分析(Reachability Analysis):从GC Roots开始向下搜索,搜索所走过的路径称为引用链。当一个对象到GC Roots没有任何引用链相连时,则证明此对象是不可用的。通过称为 “GC Roots” 的对象作为起点,从这些节点开始向下搜索,搜索路径称为 “引用链(Reference Chain)”,以下对象可作为GC Roots:
    (a)本地变量表中引用的对象
    (b)方法区中静态变量引用的对象
    (c)方法区中常量引用的对象
    (d)Native方法引用的对象
    当一个对象到 GC Roots 没有任何引用链时,意味着该对象可以被回收。
    在这里插入图片描述
    上述是jvm中堆区和方法区的结构图
    堆中可分成新生代和老年代,然后新生代又可分成(Eden区域、Survivous区域(From区域,To区域))内存占比是8:1:1。

新生代(Young generation):绝大多数最新被创建的对象都会被分配到这里,由于大部分在创建后很快变得不可达,很多对象被创建在新生代,然后“消失”。对象从这个区域“消失”的过程我们称之为:Minor GC 。

老年代(Old generation):对象没有变得不可达,并且从新生代周期中存活了下来,会被拷贝到这里。其区域分配的空间要比新生代多。也正由于其相对大的空间,发生在老年代的GC次数要比新生代少得多。对象从老年代中消失的过程,称之为:Major GC 或者 Full GC。

持久代( Permanent generation ) 也称之为 方法区(Method area):用于保存类常量以及字符串常量。注意,这个区域不是用于存储那些从老年代存活下来的对象,这个区域也可能发生GC。发生在这个区域的GC事件也被算为 Major GC 。只不过在这个区域发生GC的条件非常严苛,必须符合以下三种条件才会被回收:

1、所有实例被回收

2、加载该类的ClassLoader 被回收

3、Class 对象无法通过任何途径访问(包括反射)

GC过程

  • 第一次GC:

    在不断创建对象的过程中,当Eden区域被占满,此时会开始做Young GC也叫Minor GC,采用了GC的复制算法,速度快,因为新生代一般是新对象,都是瞬态的用了可能很快被释放的对象。

    1)第一次GC时Survivous中To区和From 区都为空,把Eden区域执行GC后存活的对象存储到To Survivous,如果To Survivous满了,Eden中剩下存活的对象存放到老年代区域。

    2)将Eden区域空间清空,此时From Survivous也是空的。

    3)From与To 互相切换标签。

  • 第二次GC:

    当第二次Eden区域被占满时,此时开始做GC,采用标记/整理算法,GC后会执行压缩,整理到一个连续的空间,这样就维护着下一次分配对象的指针,下一次对象分配就可以采用碰撞指针技术,将新对象分配在第一个空闲的区域。

    1)将Eden和From Survivous中经过GC未被回收的对象迁移到To Survivous,如果To Survious区放不下,将剩下的放入老年代区域;

    2)将Eden区域空间和From Survivous区域空间清空;

    3)From与To 互相切换标签。

第三次,第四次一次类推,始终保证S0和S1有一个空的,用来存储临时对象,用于交换空间的目的。反反复复多次没有被淘汰的对象,将会被放入Old区域中,默认15次(由参数–XX:MaxTenuringThreshold=15 决定)。

注意:

  • 虚拟机在进行MinorGC(新生代的GC)的时候,会判断要进入OldGeneration区域对象的大小,是否大于Old Generation剩余空间大小,如果大于就会发生Full GC。
  • 比较大的对象,数组等,大于某值(可配置)就直接分配到老年代,(避免频繁内存拷贝)。
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值