30

默认情况下,我在机器上启动的每个 Java 进程似乎都有两个垃圾收集器。我正在通过 JConsole 进行检查。

示例 - 对于我当前正在运行的 Eclipse。

PS MarkSweep

Collection Count - 221
Collection Time - 102118
Memory Pool Names - java.lang.String[4]

PS清除

Collection Count - 241
Collection Time - 2428
Memory Pool Names - java.lang.String[2]

我假设他们有重叠的池。当使用相同的池(Eden、survivor、old gen)时,两个垃圾收集器如何协同工作?池之间的对象移动是否没有重叠(例如调用第二种算法时从一个幸存者到另一个幸存者的移动)?即使不是,为什么每个池需要多个收集器?

我读过这篇关于 GC的文章。他们提到对不同的主要和次要 GC 使用不同的收集器,但似乎没有提到在同一个池上使用多个收集器。

4

2 回答 2

46

我假设他们有重叠的池。

这个假设是错误的。PS Scavenge 将用于年轻(eden,survivor)代,PS MarkSweep 将用于老一代。唯一的“重叠”是 PS Scavenge 将在对象存在一段时间后将其移动到老年代,然后让 PS MarkSweep 处理它们。

为不同的池设置不同的垃圾收集器的好处是,对伊甸池中的对象运行良好的算法不一定对老一代对象运行良好。

本文介绍了不同垃圾收集器协同工作的各种选项。

至于在没有空间将对象移动到老年代时发生的“主要”集合,Sun 的这份(诚然旧的)白皮书说如下:

...年轻代收集算法未运行。而是在整个堆上使用老年代收集算法。

于 2013-04-16T09:02:00.793 回答
1

形成您提供的文章:

通常,在每次次要收集期间,来自年轻代的部分幸存对象会移动到老年代。最终,tenured generation 将被填满并且必须被回收,从而产生一个majorcollection,整个堆都被回收。主要收集通常比次要收集持续更长时间,因为涉及的对象数量要多得多。

于 2013-04-16T09:08:40.247 回答