我正在处理一个应用程序,它存在内存消耗问题。如果用户在应用程序中长时间点击,就会出现OutOfMemoryException。
我使用 "ANTS Memory Profiler" 对应用程序进行了相当长的分析,我认为没有经典的内存泄漏(例如,事件处理程序防止对象被垃圾回收)。
但是,所有留在内存中的对象都有一个共同点-它们直接或间接使用标准的.NET控件(例如TextBox、Numberbox),这些控件实现了Finalizer。在 "ANTS Memory Profiler Instance Retention Graph" 中,我可以看到唯一持有对控件引用的实例是 .NET Finalizer Queue。
链接保留图(我没有足够的声望直接发布图片 :-)) --> http://i50.tinypic.com/2d6r6nn.png 因此,我调查了Finalizer线程死锁的方向(参见http://dotnetdebug.net/2005/06/22/blocked-finalizer-thread/),但是没有发现死锁的迹象。而且,与死锁理论相反的是,在使用Memory Profiler进行内存快照后,触发GC.Collect()后,视图被垃圾回收 - 或者说它们的Finalizers被执行,一切都很好。
我使用 "ANTS Memory Profiler" 对应用程序进行了相当长的分析,我认为没有经典的内存泄漏(例如,事件处理程序防止对象被垃圾回收)。
但是,所有留在内存中的对象都有一个共同点-它们直接或间接使用标准的.NET控件(例如TextBox、Numberbox),这些控件实现了Finalizer。在 "ANTS Memory Profiler Instance Retention Graph" 中,我可以看到唯一持有对控件引用的实例是 .NET Finalizer Queue。
链接保留图(我没有足够的声望直接发布图片 :-)) --> http://i50.tinypic.com/2d6r6nn.png 因此,我调查了Finalizer线程死锁的方向(参见http://dotnetdebug.net/2005/06/22/blocked-finalizer-thread/),但是没有发现死锁的迹象。而且,与死锁理论相反的是,在使用Memory Profiler进行内存快照后,触发GC.Collect()后,视图被垃圾回收 - 或者说它们的Finalizers被执行,一切都很好。
所以,这看起来像是带有Finalizer的.NET对象的正常生命周期,对吧?但在我的应用程序中,我可以点击直到OutOfMemoryException,而垃圾收集器从未运行过!
最后尝试解决问题的方法是使用GC.AddMemoryPressure(),因为视图中有许多位图,分配了相当多的非托管代码。但即使这样也无法促使垃圾收集器收集空闲内存。
因此,我认为应用程序中的某些概念存在内在错误,阻止了GC释放内存,但我绝对不知道是什么。
是否有人经历过类似的经历,并有任何线索?
最好的问候
Andi