JVM学习笔记——垃圾回收篇( 三 )


  • 虚引用实际上就是直接内存的引用,我们内存结构篇所学习的ByteBuffer就是例子
  • 系统首先会创建一个虚引用,然后这个虚引用会创建一个ByteBuffer对象,ByteBuffer对象通过unsafe来管理直接内存
  • 此外,我们的虚引用必定需要绑定一个引用队列,因为我们的byteBuffer对象是无法控制直接内存的,我们需要检测虚引用来删除
然后我们介绍虚引用的回收概念:
  • 首先我们会手动删除或者系统垃圾回收掉ByteBuffer对象
  • 这时我们的虚引用和直接内存是不会消失的,但是我们的虚引用会被带到引用队列中
  • 虚引用中携带者Cleaner对象,引用队列会一直检测是否有Cleaner对象进入,当检测到时会执行这个Cleaner方法来删除直接内存
我们需要注意的是:
  • 引用队列中检测Cleaner对象的优先级较高,所以效率相关而言比较快
终结器引用上述图片的A4对象就是终结器引用
我们下面介绍终结器引用的概念:
  • 终结器引用实际上是对象自己定义的finallize方法
  • 终结器对象同样也需要绑定引用队列,因为他需要靠终结器对象来清除内部对象
然后我们介绍终结器引用的回收概念:
  • 如果我们希望清除终结器引用的对象,那么我们需要先将终结器引用对象导入到引用队列中
  • 引用队列中同样也会一直检测是否出现终结器对象,若出现终结器对象,那么针对该终结器对象调用其内部对象的finallize方法删除
我们需要注意的是:
  • 引用队列中检测终结器对象的优先级较低,所以效率相关而言比较慢
垃圾回收算法本小节将会介绍垃圾回收的三种基本回收算法
标记清除法我们首先给出简单图示:
JVM学习笔记——垃圾回收篇

文章插图
我们来做简单解释:
  • 首先我们找出需要进行垃圾回收的部分并进行标记
  • 然后我们将该标记地址部分清除即可(注意:这里的清除仅仅是记录起始地址和终止地址,然后在其他内存占用时再次覆盖)
该算法的优缺点:
  • 执行速度极快
  • 但会产生内存碎片,当内存碎片逐渐增多会导致问题
标记整理法我们首先给出简单图示:
JVM学习笔记——垃圾回收篇

文章插图
我们来做简单解释:
  • 首先我们根据Root标记出需要垃圾回收的部分
  • 然后我们将垃圾回收的部分抛出之后,将后面的部分进行地址腾挪,使其紧凑
该算法的优缺点:
  • 不会产生内存碎片,导致内存问题
  • 速度较慢,同时整理过程中其他进程全部停止(因为会涉及内存地址重塑,进行其他进程可能会导致内存放置地址错误)
区域复制法我们首先给出简单图示:
JVM学习笔记——垃圾回收篇

文章插图
我们来做简单解释:
  • 我们准备两块完全相同的区间,将他们分为From和To区间
  • 我们首先在from区间存储数据,我们直接进行垃圾回收判定
  • 然后将需要保存的数据直接放入To区间,垃圾回收的部分不需要管理
  • 最后我们将From和To区间的定义交换,将新添加的数据放入现在的From区间(之前腾挪的To区间)
该算法的优缺点:
  • 不会产生内存碎片,相对而言比较迅速
  • 但需要占用两块相同的地址空间,导致占用空间较多
分代垃圾回收机制本小节将会介绍垃圾回收的常用机制
分代垃圾回收机制介绍我们前面已经介绍了三种垃圾回收算法,但实际上我们的垃圾回收采用的是三种方法的组合方法:

经验总结扩展阅读