Java的垃圾回收机制
java在内存中大致可以分为新生代以及老年代,其垃圾回收机制也不相同。
新生代一般会分为三部分,一块较大的Eden空间和两块较小的Survivor空间,其空间大小比例一般为8:1:1,其中可以使用的有效部分为一块Eden和一块Survivor空间,即每次新生代中可用内存空间为整个新生代空间的90%
我们使用java创建新的对象时,大部分时间都会创建在Eden空间中,当Eden没有足够的空间容纳新的对象时,就会进行一次GC(只在新生代中进行),对Eden和一个含有对象的Survivor空间(称为From)中所有对象首先进行可达性分析,并将依然存活的对象进行标记,之后将被标记的对象复制到另一个空的Survivor空间(称为To)中,最后将原有的数据清空,这样就完成了一次新生代的GC。
在成功的GC后,每个存活的对象都会有一个标记,用来记录其经历过几次GC,当其经历过指定次数(默认15)后,该对象就会存储到老年代中。
由于在java中大部分创建的对象(90%以上)都会很快的死掉,所以只留10%的空间复制有效的对象大部分时间应该是可以顺利进行的。当然肯定不能排除极端情况,当Survivor空间存储不了还存活的对象时,就会将一部分对象储存到老年代中。
当老年代的空间不足以容纳新的对象时,就会进行一次full gc(新生代老年代中都发生),在老年代中也是首先进行可达性分析,并将依然存活的对象进行标记,之后不是进行复制操作,而是让所有存活的对象都向一端移动,之后直接清理掉端边界以外的内存