简述JAVA GC回收机制,深入理解GC原理

5 篇文章 0 订阅

什么是“GC”

垃圾回收机制。

为什么要用“GC”

众所周知,JAVA 这语言,与C语言不同,Java内存(堆内存)的分配与回收由JVM垃圾收集器自动完成,比如 C语言自己定义的变量,不用时需要 自己回收这个变量 。JAVA 这就是自动完成了,自动检测,无用的垃圾,回收,从而释放内存。一个人工,一个自动化。

先看一下JVM内存结构

 

栈:存放局部变量

堆:存放所有new出来的东西

方法区:被虚拟机加载的类信息、常量、静态常量等。

程序计数器(和系统相关)

本地方法栈

堆内存就是GC管理的主要区域(知识点,重点)

然后JVM又把堆内存分三代,新生代,老年代,持久代。如下图

 

  • 新生代:分为eden ,From Survivor TO Survivor

绝大多数刚创建的对象会被分配在Eden区,其中的大多数对象很快就会消亡。Eden区是连续的内存空间,因此在其上分配内存极快。(每次新生代的垃圾回收(又称Minor GC)采用copy算法,之后再讲)

最初一次,当Eden区满的时候,执行Minor GC,将消亡的对象清理掉,并将剩余的对象复制到一个存活区From (此时,TO 是空白的,两个Survivor总有一个是空白的);

下次Eden区满了,再执行一次Minor GC,将消亡的对象清理掉,将存活的对象复制到TO 中,然后清空Eden区同时也 From 中消亡的对象清理掉,将存活的对象也复制到TO 区,然后清空From区;之后,“From”“To”会交换他们的角色,也就是新的“To”就是上次GC前的“From”,新的“From”就是上次GC前的“To”。不管怎样,都会保证名为ToSurvivor区域是空的。Minor GC会一直重复这样的过程,直到“To”区被填满,“To”区被填满之后,会将所有对象移动到年老代中。

 

如果没有填满,当两个存活区切换了几次(每进行一次MinorGC,都会在存活的对象做一个标记,加1,当标记的值大于15HotSpot虚拟机默认15次,用-XX:MaxTenuringThreshold控制,进入老年代)之后,仍然存活的对象(其实只有一小部分,比如,我们自己定义的对象),将被复制到老年代。

  • 老年代

在新生代中经历了N次垃圾回收后仍然存活的对象,就会被放到年老代,该区域中对象存活率高。老年代的垃圾回收(又称Major GC)通常使用标记-清理标记-整理算法。整堆包括新生代和老年代的垃圾回收称为Full GCHotSpot VM里,除了CMS之外,其它能收集老年代的GC都会同时收集整个GC堆,包括新生代)

当老年代的空间不足时,会触发Major GC/Full GC,速度一般比Minor GC10倍以上。

  • 持久代(永久代)

JDK8之前的HotSpot实现中,类的元数据如方法数据、方法信息(字节码,栈和变量大小)、运行时常量池、已确定的符号引用和虚方法表等被保存在永久代中,32位默认永久代的大小为64M64位默认为85M,可以通过参数-XX:MaxPermSize进行设置。GC不会在主程序运行期对永久区域进行清理,这也导致了永久代的区域会随着加载的Class的增多而胀满,最终抛出OOM异常。

所以虚拟机团队在JDK8HotSpot中,把永久代从Java堆中移除了,并把类的元数据直接保存在本地内存区域(堆外内存),称之为元空间。

元空间并不在虚拟机中,而是使用本地内存。因此,默认情况下,元空间的大小仅受本地内存限制。类的元数据放入 native memory, 字符串池和类的静态变量放入java堆中. 这样可以加载多少类的元数据就不再由MaxPermSize控制, 而由系统的实际可用空间来控制。

 

总结:

为了分代垃圾回收,Java堆内存分为3代:新生代,老年代和永久代

新的对象实例会优先分配在新生代,在经历几次Minor GC(默认15),还存活的会被移至老年代(某些大对象会直接在老年代分配)

Minor GC发生在新生代,当Eden区没有足够空间时,会发起一次Minor GC,将Eden区中的存活对象移至Survivor区。Major GC发生在老年代,当升到老年代的对象大于老年代剩余空间时会发生Major GC

发生Major GC时用户线程会暂停,会降低系统性能和吞吐量。

JVM的参数-Xmx-Xms用来设置Java堆内存的初始大小和最大值。依据个人经验这个值的比例最好是1:1或者1:1.5。比如,你可以将-Xmx-Xms都设为1GB,或者-Xmx-Xms设为1.2GB1.8GB

Java中不能手动触发GC,但可以用不同的引用类来辅助垃圾回收器工作

  • 5
    点赞
  • 29
    收藏
    觉得还不错? 一键收藏
  • 6
    评论

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

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值