G1GC区域内压缩

4
据我所知,G1 GC执行疏散操作以从年轻区域和老年区域回收堆,从而间接压缩堆(将活动对象从待收集区域复制到空白区域)。那么,G1 GC是否会出现这样一种情况:没有完全空的区域可用于复制对象,但半满区域中有足够的分散堆?我想问一下,G1是否跟踪区域内的空闲空间,并在区域内进行压缩?
2个回答

5

HotSpot VM垃圾回收调优指南分配(疏散)失败部分中提到:

如果在垃圾回收区域的疏散过程中找不到空闲(空)区域,则会发生分配失败(因为没有空间来分配从正在疏散的区域中存活的对象),并且会进行停止-全局(STW)回收。

虽然没有明确说明,但这意味着STW全局回收能够执行压缩,否则它就不是解决碎片问题的方法。我只在巨大对象和巨大分配部分找到了关于压缩能力的间接提示:

为了减少复制开销,巨型对象不包含在任何疏散暂停中。完整的垃圾回收周期会原地压缩巨型对象。
这并不意味着“G1跟踪区域内的空闲空间”,因为这样做默认情况下执行复制将失去意义,而是,这个必要的信息可能会在完整的垃圾回收过程中获取。

最近我非常惊讶于网上关于这些有趣话题的信息是如此之少。在研究了两天G1源代码后,我几乎可以确定你是正确的。尽管每个GC周期中某个区域的活跃度和大小都是众所周知的,但理论上这是可能的。 - Eugene
2
通常情况下,需要选择垃圾最多的地区时,需要了解各个地区垃圾比例的一般信息,而关于区域内仍可访问对象之间差距的详细信息则不是复制收集器所需的,这也是复制收集器的优点之一。因此,尽可能避免维护该信息是很直接的。 - Holger
你是正确的,我理解这一点,这甚至可以通过G1ReservePercent的存在来暗示... - Eugene

-2
G1(垃圾收集器)何时开始运行,以及它首先收集哪个内存区域?
堆被分成许多等效的估计堆区域,每个区域都是虚拟内存的一个接触范围。类似的工作被分配给某些区域集(eden、survivor、old)。
G1执行同时全局标记阶段,以确定整个堆中对象的活动状态。标记阶段完成后,G1知道哪些区域大部分为空。它首先收集这些区域,这通常会产生大量的可用空间。这就是为什么这种垃圾收集方法被称为“垃圾优先”的原因。正如名称所示,G1将其收集和压缩活动集中在堆的那些可能充满可回收对象(即垃圾)的区域上。G1使用中断预测模型来满足用户定义的停顿时间目标,并根据指定的停顿时间目标选择要收集的区域数量。
G1通过清除操作收集垃圾的存储区域,以识别可恢复的本地。 G1将对象从一个或多个存储区域复制到堆栈上的单个区域中,并在此过程中紧缩和释放内存。此过程在多处理器上并行执行,以减少停止时间并增加吞吐量。因此,对于每个垃圾收集,G1始终尝试减少碎片,在用户定义的延迟时间内工作。这超出了以前方法的能力。
基本上,跟踪每个区域中的实时数据量,并在触发收集时首先清除垃圾最多的部分。
这意味着它也可以从半满的区域收集垃圾。

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接