四、对象创建和垃圾回收流程

在这里插入图片描述
在Java中支持GC的概念,GC有两种调用形式:自动调用、手工调用:

(Runtime.getRuntime().gc()

在写代码的时候,很少手工调用,因为不是实时的。那为什么不是实时的?因为GC不是把没用的空间腾出来就完毕了。比如说,有十处垃圾点,直观感受回收就是把垃圾挪出去就行,其实不是。因为一旦要进行GC,至少应该先找到垃圾,而后再把垃圾的空间填新东西。

自动调用

JVM什么时候会自动调用呢?回答这个问题,就牵扯到了两类的GC操作环境。先看下图
在这里插入图片描述
Eden:伊甸园 Survivor:存活区 Tenured:老年区

  1. 当程序之中需要产生新的实例化对象(关键字new、对象克隆、反射实例化)的时候,因为一定要进行内存空间的开辟,所以此时需要申请新的内存空间
  2. 新对象要申请的对象的空间默认都在伊甸园区(新生)进行开辟,因此需要判断伊甸园区是否有空余的内存空间。
  3. 如果有空余的内存空间,则直接在伊甸园区开辟新的堆内存空间,此时不会发生有GC处理;
  4. 如果新对象无法在伊甸园空间申请出新的空间,那么就表示现在的伊甸园的空间不足,不足就需要将那些无用的新对象进行回收(此时叫Minor GC)
  5. 当回收完毕后还要判断该空间是否有空余的空间可以容纳新的对象,如果可以容纳,则开辟新空间,保存新对象
  6. 如果此时伊甸园区即时执行了Minor GC后发现依然没有可以被回收的对象,那么这时候就会判断存活区是否有空间(存活区一般与伊甸园的比率是 1:1:8)
  7. 如果存活区有空余空间,则将那些活跃的伊甸园区的部分对象直接保存给存活区,这样就相当于伊甸园区可以腾出部分的空间(这个空间非常的小)来,供新对象进行使用
  8. 如果此时存活区依然满了(空间不足),则继续向老年代进行内存空间的申请。向老年代进行空间的申请,首先会判断老年代的空间是否空余
  9. 如果空余则将存活区中的活跃对象保存在老年代,而后存活区得到了空间释放,伊甸园区得到了空间释放,则对象空间申请成功
  10. 如果老年代也是满的,那么这个时候会执行FULL GC(又叫完全GC、major GC)进行老年代的内存释放
  11. 如果释放成功,则进行对象的保存,如果释放不成功则表示已经没有无用的内存空间了,那么就会抛出OOM(OutOfMemoryError)

这就是对象的创建以及垃圾回收流程,也是GC自动操作的触发条件
S0:S1:Eden=1:1:8
关于上面流程还有一个面试题:自动的GC什么时候触发?
GC的触发有两类:

  • Minor GC:发生在年轻代内存空间,当年轻代内存空间不足时会进行触发,释放年轻代中不活跃的对象
  • Full GC(Major GC):发生在老年代的内存空间,当老年代的内存空间不足时会自动触发Full GC,如果触发Full GC之后,内存空间依然不足,则会产生OutOfMemoryError的错误信息
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 1
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值