新生代Minor GC 后剩余存活对象太多,无法放入 Survivor 区中,此时就必须将这些存活对象直接转移到老年代去,如果此时老年代空间也不够怎么办?
1、执行任何一次 Minor GC 之前,JVM 会先检查一下老年代可用内存空间,是否大于新生代所有对象的总大小,因为在极端情况下,可能新生代 Minor GC 之后,新生代所有对象都需要存活,那就会造成新生代所有对象全部要进入老年代:
2、如果老年代的可用内存大于新生代所有对象总大小,此时就可以放心大胆的对新生代发起次 Minor GC,因为 Minor GC之后即使所有对象都存活,Survivor 区放不下了,也可以转移到老年代去;
3、如果执行 Minor GC 之前,检测发现老年代的可用空间已经小于新生代的全部对象总大小那么就会进行下一个判断,判断老年代的可用空间大小,是否大于之前每一次 Minor GC 后进入老年代的对象的平均大小,如果判断发现老年代的内存大小,大于之前每一次 Minor GC后进入老年代的对象的平均大小,那么就是说可以冒险尝试一下 Minor GC,但是此时真的可能有风险,那就是 Minor G 过后,剩余的存活对象的大小,大于 Survivor空间的大小,也大于老年代可用空间的大小,老年代都放不下这些存活对象了,此时就会触发一次“Full GC”; 所以老年代空间分配担保机制的目的? 也是为了避免频繁进行 Full GC;
4:如果 Full GC之后,老年代还是没有足够的空间存放 Minor GC 过后的剩余存活对象,那么此时就会导致“OOM”内存溢出