前往小程序,Get更优阅读体验!
立即前往
首页
学习
活动
专区
工具
TVP
发布
社区首页 >专栏 >JVM学习-垃圾回收

JVM学习-垃圾回收

作者头像
sgr997
发布2022-11-10 13:45:47
2450
发布2022-11-10 13:45:47
举报
文章被收录于专栏:博客分享
代码语言:javascript
复制
网上学习的JVM课程,跟随视频自己做的笔记

一、如何判断对象是否可以被回收:
1. 引用计数法:对象被其他对象引用计数+1,不再引用就-1,0就表示可以被回收掉了。
  • 弊端:如果两个对象互相引用,各自的计数都是1,但是没有其他对象引用他们,就不能被回收。
在这里插入图片描述
在这里插入图片描述

2. 可达性分析算法:

  • 垃圾回收之前,会对堆内存进行扫描,来检测每个对象是否会被根对象(GC Root)直接或间接引用,如果是那么这个对象不能被回收,反之则可以回收。
  • 举个例子:像一串葡萄一样,如果把葡萄从顶部提起来,跟随葡萄一同起来的葡萄果代表不能被回收的对象,而那些断开散落的则是能被回收的对象。
  • 哪些对象可以被作为GC Root? 可以通过eclipse提供的工具Memory Analyzer来分析。 System Class(系统核心类)、Native Stack、Busy Monitor(正在加锁的对象)、Thread(活动线程类)、栈帧内使用的对象。 比如一个方法内声明了List list = new ArrayList<>();则该ArrayList即可作为GC Root。3. 四种引用(细分有五种) 3.1 强引用 Obj obj = new Obj(); 只要所有GC Roots对象都不通过强引用引用该对象,该对象才能被回收。3.2 软引用(SoftReference)
  • 仅有软引用引用该对象时,在垃圾回收后,内存仍不够才会回收软引用对象。
  • 可以配合引用队列来释放软引用自身
  • 适用场景:数据缓存3.3 弱引用(WeakReference)
  • 仅有弱引用引用该对象时,在垃圾回收时,无论内存是否充足,都会回收弱引用对象。
  • 可以配合引用队列类释放弱引用自身3.4 虚引用(PhantomReference幽灵引用)
  • 必须配合引用队列使用,主要配合ByteBuffer使用,被引用对象回收时,会将虚引用入队列,由Reference Handler线程调用虚引用相关方法释放直接内存。3.5 终结器引用(FinalReference)
  • 无需手动编码,但其内部配合引用队列使用,在垃圾回收时,终结器引用入队(被引用对象暂时没有被回收),再由Finalizer线程(优先级低)通过终结器引用找到被引用对象并调用他的finalize方法,第二次GC时才能回收被引用对象。二、 垃圾回收算法 JVM会根据情况采用下面三种算法。
  • 1. 标记清除(Mark Sweep) 先标记再清除,效率相对来说快,但是会产生内存碎片,造成内存不连续。 优点:效率高 缺点:会产生内存碎片
  • 2. 标记整理(Mark Compact) 标记清除完会对内存进行整理, 将可用对象向前移动使内存更加连续,还要更新对象的引用地址,所以效率相对来说较低。 优点:不会产生碎片 缺点:效率相对较低
  • 3. 复制(Copy) 将内存区域划分为两块区域,from区域和to区域,先找到存活的对象进行标记,将存活的对象复制到to并且进行内存整理,然后将from和to进行交换。 优点:不会产生碎片 缺点:占用双倍的内存空间
  • 三、 分代垃圾回收机制
在这里插入图片描述
在这里插入图片描述
  1. 创建新的对象时,默认采用伊甸园的内存
  2. 当伊甸园内存不足时,会发生Minor GC,对伊甸园进行一次垃圾回收,并采用复制算法将对象存放在幸存区to,年龄+1(to和from会交换位置)
  3. 经过第一次垃圾回收之后,伊甸园的内存又充足了,当伊甸园内存再次不足时会发生第二次Minor GC,此时会对伊甸园和幸存区from进行垃圾回收,也会将存活的对象存放到to,年龄+1并交换to和from位置。
  4. 存活的对象不会一直在幸存区,当年龄超过一定的阈值(最大为15,因为是4bit,最大为1111)会认为该对象价值高经常被使用,会晋升至老年代。
  5. 当新生代和老年代内存都不足时会先尝试Minor GC,如果仍不足,会触发Full GC,来进行整个内存清理。
  6. 补充:GC时,会发生STW(stop the world)(因为采用复制算法,对象的地址会发生改变),暂停其他用户线程,等待垃圾回收结束,用户线程才恢复运行。Full GC的STW时间更长。四、相关VM参数
在这里插入图片描述
在这里插入图片描述
五、垃圾回收器
1、串行垃圾回收器
在这里插入图片描述
在这里插入图片描述

开启指令:-XX:+UseSerialGC=Serial+SerialOld Serial为新生代垃圾回收器,采用复制算法。 SerialOld为老年代,采用标记+整理算法。 都为单线程的,垃圾回收时都会STW。

2、吞吐量优先垃圾回收器
在这里插入图片描述
在这里插入图片描述

参数一:并行的垃圾回收器,JDK1.8默认的垃圾回收器。 参数二:采用自适应调整伊甸园,晋升阈值和幸存区大小。 两个目标: 参数三:计算公式:1/(1+ratio),比如radio是99,则公式得0.01,即100分钟内最多有1分钟来进行垃圾回收,如果达不到这个目标则会调整堆内存,一般是调大,来减少垃圾回收的次数,来提高系统吞吐量。一般设置19。 参数四:最大停留ms数,默认200ms。与上边是冲突的,因为如果上边有做出调大堆内存,那么停留时间可能就会变长,导致达不到这一目标。 这两个是冲突的。 参数五:控制垃圾回收时并行的线程数量。

3、响应时间优先的垃圾回收器(CMS)
在这里插入图片描述
在这里插入图片描述

-XX:+UseConcMarkSweepGC ~ -XX:+UseParNewGC ~ SerialOld 是工作在老年代基于标记清除算法的垃圾回收器,并发失败会降级为SerialOld串行垃圾回收器。 初始标记和重新标记会STW,初始标记只标记根对象,因为并发标记时用户线程也在执行,会产生新的垃圾,所以需要重新标记。

本文参与 腾讯云自媒体同步曝光计划,分享自作者个人站点/博客。
原始发表:2021-12-04,如有侵权请联系 cloudcommunity@tencent.com 删除

本文分享自 作者个人站点/博客 前往查看

如有侵权,请联系 cloudcommunity@tencent.com 删除。

本文参与 腾讯云自媒体同步曝光计划  ,欢迎热爱写作的你一起参与!

评论
登录后参与评论
0 条评论
热度
最新
推荐阅读
目录
  • 一、如何判断对象是否可以被回收:
    • 1. 引用计数法:对象被其他对象引用计数+1,不再引用就-1,0就表示可以被回收掉了。
    • 五、垃圾回收器
      • 1、串行垃圾回收器
        • 2、吞吐量优先垃圾回收器
          • 3、响应时间优先的垃圾回收器(CMS)
          领券
          问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档