一.两种回收策略

  • 引用计数法
    给对象添加一个引用计数器,每当有一个地方引用它,计数器就加1;当引用失效,计数器就减1;任何时候计数器为0的对象就是可被回收的对象.
    该方法实现简单,效率高,但是目前主流的虚拟机中并没有采用该策略管理内存,最主要的原因是它很难解决对象直接相互循环引用的问题,但是它们由于相互引用导致计数器都不为0,浴室引用计数器无法通知GC回收器回收它们.

  • 可达性分析算法
    将"GC Roots"对象作为起点,从这些夹断开始向下搜索引用的对象,找到的对象全部标记为非垃圾,其余未标记的对象都是垃圾对象.
    GC Roots的判断方法:一般为线程栈的本地变量,静态变量,本地方法栈的变量等等.

二.垃圾回收算法

  • 1标记清除算法
    垃圾回收专题 特点:清除后空闲位置不连续,容易产生碎片

  • 2复制算法
    垃圾回收专题将内存分割,存活对象复制到没有使用过的另一半内存中,可回收的对象的清除,虽然降低了碎片,但是空间使用率低

  • 3标记整理

垃圾回收专题
将内存中可回收对象标记回收后把存活对象进行整理,虽然没有碎片但是效率低

常用垃圾回收器

垃圾回收专题
图中连线表示可以配对使用
java1.8之前的堆内存采用分代的概念.

垃圾回收专题

serial采用单线程复制算法,暂停所有用户线程,用于新生代

垃圾回收专题

serial old采用单线程标记整理算法,暂停所有用户线程,用于老年代

parallel scavenge和parallel old(PSPO)是1.8默认收集器

垃圾回收专题

parallel scavenge采用多线程复制算法,暂停所有用户线程,用于新生代
垃圾回收专题

parallel old采用多线程标记整理算法,暂停所有用户线程,用于老年代

上述两种都会导致用户线程暂停!
垃圾回收专题

par new 采用采用多线程复制算法,暂停所有用户线程,用于新生代
垃圾回收专题

CMS (ConcurrentMarkSweep)采用标记清除算法

  • 第一阶段:标记gcRoots连接的第一个对象(该过程会暂停所有用户线程,但时间极短)
  • 第二阶段:并发标记,继续沿第一阶段标记的对象往下标记(该过程和用户线程并发,可能会产生浮动垃圾甚至误标垃圾,浮动垃圾可在下次GC回收)
  • 第三阶段:重新标记,解决误标垃圾问题(该过程会暂停所有用户线程,但时间极短)
  • 第四阶段:并发清理,清理垃圾(该过程和用户线程并发,考虑极端情况下,此时老年代新的垃圾放不下,会立即终止CMS,转而采用serial old替补)

CMS的效率在毫秒级

java1.8之后没有分代的概念,只有分区的概念
java1.9默认收集器G1特点是一边运行一边回收 比CMS效率更高
java1.9及以后的垃圾回收器且听下回分解

相关文章:

猜你喜欢
  • 2021-10-17
  • 2022-12-23
  • 2021-08-02
  • 2021-11-18
  • 2021-10-26
相关资源
相似解决方案