JVM垃圾回收机制

什么是可回收的垃圾对象?

栈里面的变量没有指向堆里面的对象,则堆里面的对象为垃圾对象


01-何为垃圾对象.png

如何找到垃圾对象

引用计数法

引用计数法.png

可达性分析算法

可达性分析算法.png

GC算法

标记-清楚算法

标记-清楚算法.png

复制算法

复制算法将内存划分为两个区间,一个活动区间,一个空闲区间,其中活动区间存放的是动态分配的对象。

复制算法从根集合扫描活动区间,将存活的对象复制到空闲区间。扫描完毕后,将活动区间清空。把原本的空闲区间变成活动区间。以此循环。

复制算法在存活对象比较少的时候,极为高效,利用空间换来时间。所以复制算法的使用场景,必须是对象的存活率非常低才行,而且最重要的是,我们需要克服50%内存的浪费。


复制算法.png

标记-整理算法

标记-整理算法从根集合进行扫描,对存活的对象进行标记,标记完毕后,再扫描整个空间中未被标记的对象进行直接回收。回收不存活的对象之后,会将所有存活的对象往左端空闲空间移动。避免产生内存碎片。


标记-整理算法.png
区别:
  1. 标记-清楚——位置不连续,产生内存碎片
  2. 复制算法——没有碎片,但是会浪费空间,每次只使用一半的内存去做垃圾回收
  3. 标记整理——没有碎片,但是效率低下,需要整理内存

java内存分代模型

java内存分代模型.png

常用垃圾收集器

05-常见的垃圾收集器.png

jdk 8的回收机制

分代回收机制

新生代

  • 绝大多数刚被创建的对象
  • 在创建后很快变得不可达,被 JVM 回收
  • 对象从这个区域被回收的过程称为 Minor GC
  • 回收算法:复制算法

空间分配

  • 一个伊甸园空间(Eden)
  • 两个幸存者空间(From Survivor、To Survivor)
  • 默认新生代空间的分配:Eden : From : To = 8 : 1 : 1

执行顺序

  1. 大多数刚被创建的对象会存放在伊甸园空间
  2. 伊甸园执行第一次 Minor GC 之后,存活的对象会移动到其中一个幸存者空间
  3. 此后每次伊甸园每次 GC 都会将存活的对象堆积到同一个幸存者空间
  4. 当一个幸存者空间满了之后,还存活的对象会移动到另一个幸存者空间,然后清空饱和的那个幸存者空间
  5. 在以上步骤中重复N次(N = MaxTenuringThreshold(年龄阀值设定,默认15))依然存活的对象,就会被移动到老年代
从上面的步骤可以发现,两个幸存者空间,必须有一个是保持空的。
对象在刚刚被创建之后,是保存在伊甸园空间的(Eden)。那些长期存活的对象会经由幸存者空间(Survivor)转存到老年代空间(Old generation)。
也有例外出现,对于一些比较大的对象(需要分配一块比较大的连续内存空间)则直接进入到老年代。一般在Survivor 空间不足的情况下发生。

老年代

  • 对象没有变得不可达,并且从新生代周期中存活了下来,会被拷贝到这里
  • 该区域分配的空间要比新生代多。
  • GC次数要比新生代少得多。
  • 对象从老年代中被回收的过程,称为 Full GC 或者 Major GC
  • Major GC 的时间比 Minor GC 要更长
  • 回收算法:标记-整理算法

持久代

  • 也称为方法区(即Java内存模型中的方法区)
  • 保存类常量以及字符串常量
  • 发生在这个区域的GC事件也被算为Major GC

发生GC的条件非常严苛,必须符合以下三种条件:

1.所有实例被回收
2.加载该类的ClassLoader被回收
3.Class对象无法通过任何途径访问(包括反射)

GC 执行时机

新生代的伊甸园空间(Eden)不够存放新对象的时候,执行 Minro GC 。

升到老年代的对象大于老年代剩余空间的时候(或者小于的时候被 HandlePromotionFailure 参数强制)执行 Full GC 。

最后编辑于
©著作权归作者所有,转载或内容合作请联系作者
【社区内容提示】社区部分内容疑似由AI辅助生成,浏览时请结合常识与多方信息审慎甄别。
平台声明:文章内容(如有图片或视频亦包括在内)由作者上传并发布,文章内容仅代表作者本人观点,简书系信息发布平台,仅提供信息存储服务。

相关阅读更多精彩内容

友情链接更多精彩内容