在.NET等托管环境中是否可能发生内存泄漏?

sha*_*oth 8 .net c# memory-leaks memory-management

在C++中,很容易产生永久性内存泄漏 - 只需分配内存而不释放内存:

new char; //permanent memory leak guaranteed
Run Code Online (Sandbox Code Playgroud)

并且该内存在堆的生命周期内保持分配(通常与程序运行时的持续时间相同).

在C#程序中是否可以(在内存管理机制正常工作的情况下导致特定的未引用对象的情况相同)?

我仔细阅读了这个问题并给出了答案,它提到了一些导致内存消耗高于预期的情况或IMO相当极端的情况,比如终结器线程死锁,但是在正常运行的C#程序中会形成永久性泄漏内存管理?

jal*_*alf 25

这取决于您如何定义内存泄漏.在非托管语言中,我们通常将内存泄漏视为已分配内存的情况,并且不存在对它的引用,因此我们无法释放它.

在.NET中创建这种泄漏几乎是不可能的(除非你调用非托管代码,或者除非运行时有错误).

但是,你可以得到泄漏的另一种"弱"的形式:当对内存的引用存在的(所以还是有可能找到并重新设置参考,允许GC来释放正常的内存),但你认为它没" t,所以你假设被引用的对象会得到GC.这很容易导致内存消耗的无限增长,因为你正在堆积对不再使用的对象的引用,但是它们不能被垃圾收集,因为它们仍然在应用程序的某处被引用.

因此,在.NET中通常被认为是内存泄漏的情况只是您忘记了对对象的引用(例如,因为您未能取消订阅事件).但是参考文献存在,如果你记得它,你可以清除它,泄漏就会消失.

  • 如果一个程序不停地将一些东西扔进一个它从不麻烦的集合中,因为程序员忘了这样做,我真的不会认为是内存泄漏.另一方面,如果对某个对象的引用存在于一个表单中,该表单的删除需要不再存在的信息,那么这将是一个内存泄漏.例如,如果事件订阅者被放弃,除非发布者使用复杂的欺骗来模拟弱事件,否则只要发布者在范围内,就可能无法取消订阅事件. (2认同)