内容提要
在2026年Python语言峰会上,Mark Shannon提出结合分代与增量垃圾回收的新方案。此前Python 3.14的增量GC因内存压力被回退。他定义“清扫有效性”等概念,指出当前GC有效性仅0.3%至1%。新方案设年轻与年老两代,交替增量清扫,年轻代初始20MB,以兼顾低内存与低暂停。与会者讨论调优、测试用例及并发GC可行性,Mark强调需先收集实际数据再决策。
延伸解读
分代与增量:为何难以兼得
分代GC利用“大多数对象早死”的假设,内存占用低,但暂停时间可能长达数秒;增量GC通过将回收工作分片,将暂停降至数十毫秒,却因非分代设计导致内存压力增大。Python 3.14的增量GC因生产环境内存问题被回退,正体现了这一权衡。Mark Shannon的新提案试图结合两者,但如何平衡仍是核心挑战。
清扫有效性:一个被忽视的指标
Mark Shannon提出“清扫有效性”概念,即回收对象数与访问对象数之比。当前Python分代GC的有效性仅0.3%,增量GC约1%,意味着GC花费大量时间访问对象却回收甚少。这解释了为何GC占执行时间约11.67%。提高有效性是优化GC的关键方向,但需注意Python以引用计数为主,GC只是处理循环引用的后备机制。
调优与测试:社区分歧的焦点
与会者对GC调优态度不一。Donghee Na建议提供类似JVM的配置选项,但Mark认为Python的GC是“后备”,无需复杂调优。Gregory P. Smith强调应将不同GC适用的用例纳入测试套件,避免升级时出现意外。Pablo Galindo和Thomas Wouters则指出生产环境调优对修复病态行为和推动版本升级至关重要。Mark回应需先收集实际数据再决策。
并发GC的可行性:障碍与前景
Larry Hastings询问并发或“无锁”GC的可能性,Mark Shannon指出实现难度极大,且C扩展可以任意操作内存,会干扰无锁并发收集器。Tobias Wrigstad补充说,并发无锁GC需要侵入式修改,例如在每个指针中嵌入元数据。因此,尽管“免费回收内存”很诱人,但在Python生态中短期内难以实现。
Q&A
Python 3.14 的增量垃圾回收器为什么被回退?
因为生产环境中报告了“显著的内存压力”,所以 Python 3.14 的增量垃圾回收器被回退为 Python 3.13 的分代垃圾回收器。
Mark Shannon 提出的新垃圾回收方案具体是什么?
新方案结合分代与增量垃圾回收:设年轻和年老两代,交替进行增量清扫;年轻代初始固定为 20MB;年老代的清扫频率是年轻代存活率的两倍。
什么是“清扫有效性”?当前 Python 垃圾回收器的有效性如何?
清扫有效性是“收集的对象数”除以“访问的对象数”。当前分代 GC 的有效性约为 0.3%,被回退的增量 GC 约为 1%,都“相当差”。
分代垃圾回收和增量垃圾回收各有什么优缺点?
分代 GC 整体内存占用更低,但暂停时间更长;增量 GC 暂停时间更短(峰值暂停从约 3 秒降至几十毫秒),但代价是内存占用更高。
与会者对于垃圾回收器的调优和配置有哪些讨论?
有人询问是否提供类似 JVM 的配置选项,Mark 认为没必要,因为 Python 的 GC 只是引用计数的“备份”。也有人建议提供“CPU 预算”机制,但可能导致无法回收所有死内存。Pablo 和 Thomas 提到在生产中实时调优 GC 以修复病态行为,并认为这是升级 Python 版本的常见障碍。Mark 强调需要先收集这些实际数据再决策。
Python 中实现并发或免锁垃圾回收器面临哪些挑战?
实现非常困难,且 C 扩展可以“为所欲为”,会干扰免锁并发收集器;此外,并发免锁 GC 需要侵入性地在每个指针中嵌入元数据。