Python - 内存泄漏

8 投票
2 回答
6011 浏览
提问于 2025-04-15 21:51

我正在解决我Python应用中的内存泄漏问题。

事情是这样的——这个问题似乎只在Windows Server 2008(不是R2版本)上出现,而在更早的Windows版本上没有发现这个问题,同时在Linux上也没有看到这个现象(不过我在Linux上的测试还不够多)。

为了排查这个问题,我在垃圾回收器上设置了调试:

gc.set_debug(gc.DEBUG_UNCOLLECTABLE | gc.DEBUG_INSTANCES | gc.DEBUG_OBJECTS)

然后,我定期记录gc.garbage的内容。

奇怪的是,gc.garbage总是空的,但我的内存使用量却一直在增加。

这真让人困惑。

2 个回答

3

一般来说,Python中的内存泄漏主要是由于C扩展引起的。
你有没有使用这些扩展呢?

另外,你提到这个问题只在2008系统上出现;我建议你检查一下扩展是否有不兼容的情况,因为在Vista和2008之间有很多小的变化,这些变化可能会导致问题。
作为替代方案,可以尝试在Windows兼容模式下运行你的应用程序,选择Windows XP,这可能有助于解决问题,特别是如果这个问题和安全性变化有关的话。

25

如果gc.garbage里从来没有垃圾对象,那我就不太明白你开启GC调试的目的是什么。没错,它会告诉你哪些对象被考虑清理,但如果你没有那些无法清理的循环引用,那这其实没什么特别的意思。

如果你的程序在操作系统中显示占用的内存越来越多,通常可能有四种情况:

  1. 你的应用程序存储了越来越多的东西,并且保持对每个对象的引用,这样它们就不会被清理掉。
  2. 你的应用程序在对象之间创建了循环引用,这些引用是gc模块无法清理的(通常是因为其中一个对象有一个__del__方法)。
  3. 你的应用程序在释放(并重新使用)内存,但操作系统不想重新使用这些内存,所以它不断分配新的内存块。
  4. 真正的内存泄漏发生在你的代码使用的C/C++扩展模块中。

根据你的描述,情况#1似乎不太可能(因为在任何操作系统上都会表现得一样),而且显然也不是情况#2(因为gc.garbage里没有任何东西)。考虑到情况#3,Windows(一般来说)有一个在碎片化分配方面表现不佳的内存分配器,但Python通过它的obmalloc前端来解决这个问题。不过,这可能还是与Windows Server 2008的系统库有关,让你的应用程序看起来占用的内存越来越多。或者可能是情况#4,即你使用的C/C++扩展模块,或者Python或扩展模块使用的DLL中存在内存泄漏。

撰写回答