为啥老年代的Full GC要比新生代的Minor GC慢很多倍

  1. 从执行过程来看,新生代执行速度快,因为直接从GCroot触发就追踪哪些对象是活的,新生代存活对象比较少。老年代的并发标记阶段,需要追踪所有存活对象,老年代存活对象很多,过程就很慢。并发清理阶段,也不是一次性回收一片内存,而是零零散散回收,如果剩余空间不足于放要进入的老年代对象,还会引起 concurrent mode failure,要调用serial old,重新stop the world清理。很耗时

    触发老年代GC的时机

  2. 老年代可用内存小于新生代全部对象大小,如果没开启空间担保参数,会直接触发Full GC.

  3. 老年代可用内存小于历代新生代GC后进入老年代的平均对象大小,会提前触发GC
  4. 新生代Minor GC后的存活对象大于Survivor,会进入老年代,老年代内存不足,会导致老年代GC
  5. 设置-XX:CMSInitatingOccupancyFaction参数,如果老年代可用内存大于历代新生代GC后进入老年代的平均大小,但是老年代已经使用的内存空间超过了这个参数的指定比例,也会触发Full GC