jvm垃圾回收机制_jvm系列三:垃圾回收机制之新生代和老年代

1、前文回顾

上一篇文章(jvm内存区域如何区分)主要介绍了jvm各个内存区域方法区、程序计数器、虚拟机栈、堆内存、本地方法栈,并使用一段代码,介绍如何使用各个内存区域的。简单回顾下:

4abef840cdcba2d56d7e995a1fabc7dd.png

我们从上一篇文章中知道,虚拟机栈中的栈帧的局部变量表存放着方法中的局部变量,这些局部变量都引用着堆内存中各种对象的内存地址。当我们一个方法执行完后,栈帧就会出栈,意味着我们的局部变量也会立即被销毁,但是此时我们堆内存中的对象呢?会不会立即就被销毁掉?答案是不会的,因为我们jvm有垃圾回收机制,一旦我们启动jvm进程,后台有一条垃圾回收线程,定时检查我们堆内存中的对象,当这些对象没有被引用的时候就会被垃圾回收器回收掉。

678bd3e5e014211a0a5aec0b3bd25674.png

2、年轻代和老年代

在讲垃圾回收机制之前,我们来先讲一下堆内存的划分,堆内存主要划分为两个区域:新生代和老年代。其实我们创建的绝大多数的对象的存活周期是很短的,只有少部分的对象的存活周期比较长,那么这些存活周期短的对象我们会放在新生代中,存活周期长的对象会放在老年代中。

1bee19565e369cdd93b9cea832ba5fc0.png

看到这里我们可能会想,为什么我们要区分新生代和老年代呢?其实,这跟垃圾回收有关系,我们都知道新生代存放的是存活周期短的对象,老年代存放长期存在的对象,那么对于这两种对象,我们有各自的垃圾回收算法,所以才去区分。

3、对象什么时候进入新生代

既然我们都知道了新生代和老年代存放着什么样的对象,那么又有一个问题来了,对象是什么时候进入新生代的呢?我们先来看一段代码:

f37c72b93aa39ab9ab1ec9feea7d9f62.png

从上面这段代码中,我们创建了User和ResourceManager两个对象,这两个对象一旦创建,就会放在新生代中,我们用下图表示:

6d636f3be1d8c0589c670b1d161c6cc3.png

当代码执行完load()方法后,那么load栈帧会出栈,局部变量resourceManager的引用会被销毁如下图:

4872b9fd268456e9b0bd08559fdb0bbf.png

这个时候,新生代中的ResourceManager对象没有被任何对象引用,当然这个时候并不会被立马回收掉,而是要等到新生代空间不足时,才会触发垃圾回收,从而腾出更多的新生代的内存空间给其他新创建的对象使用,这种回收称为Minor GC或者Young GC。如下图:

908ec3c651e4e9afda55b15ce2184d92.png

4、对象什么时候进入老年代

我们从上图可以看出,User实例一直被Main类里面的静态变量user引用着,即使你的新生代经过很多次回收,依然回收不掉这个对象,因为别人引用着它。jvm有一个规定,对象在新生代如果连续躲过15次垃圾回收,那么这个对象就会从新生代进入老年代。那这样看起来,User对象就进入了老年代,那什么时候会被回收掉呢?当然,当老年代空间不足的时候,老年代里的对象也会被回收掉,具体的细节,我们后面文章会继续讲。好了,今天这篇文章就写到这里,下篇再见。

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值