看过这个图,应该不用多加解释,反正就是堆分成上下两个区域,哪部分满了,活动对象往另一部分跑,被移出的区域剩下的对象全是垃圾,可以哗一下全清空。来来回回,新对象总是在正用的那部份分配。想想你在运行 Java 程序的时候应该有过突然被中止不动的时候,可能就是 GC 在活动了。
分代收集器
简单的停止拷贝收集器的缺点是,每次收集时,所有的活动对象都要移动来移动去。对于短生命的对象还好说,经常可以就地解决掉,可是对于长生命周期的对象就纯粹是个体力劳动了,把它挪来挪去除消耗大量的时间,没有产生任何效益。分代收集能直接让长生命周期的对象长时间的呆在一个地方按兵不动。GC 的精力可以更多的花在收集短命对象上。
这种方法里,堆被分成两个或更多的子堆,每一个堆为一“代”对象服务。最年幼的那一代进行最频繁的垃圾收集。因为多数对象是短命的,只有很小部分的年幼对象可以在经历第一次收集后还存活。如果一个最年幼的对象经历了好几次垃圾收集后仍是活着的,那这个对象就成为寿命更高的一代,它被转移到另外一个子堆中去。年龄更高一代的收集没有年轻一代来得频繁。每当对象在所属的年龄代中变得成熟(多次垃圾收集后仍幸存)之后,就可以转移到更高年龄的一代中去。
分代收集除了可应用于拷贝算法,也可以应用于标记清除算法。不管在哪种情况下,把堆按照对象年龄分组可以提高最基本的垃圾收集的性能。