C# – 试图找到剩余的EventHandler,防止控件超出范围

长话短说,我inheritance了一个相当复杂的应用程序,我试图追踪涉及表单的内存泄漏。 现在,每次关闭表格并提出新表格时,旧表格仍留在记忆中。 我跟踪了一个由程序中的控件拥有和设置的静态事件的问题(显然,只要静态事件被设置,该控件的任何实例都不被认为超出了范围,即使没有其他人提到所述控件)。 现在,我正在努力追查剩下的问题。

使用MemProfiler和ANTS Memory Profile,我了解到根执行路径如下:

FormOpenWatch <-- The item which remains active System.EventHandler -- (this as Delegate)._target System.Object[] System.EventHandler -- (this as MultiCastDelegate)._invocationList System.ComponentModel.EventHandlerList+ListEntry -- handler System.ComponentModel.EventHandlerList+ListEntry -- next System.ComponentModel.EventHandlerList+ListEntry -- next System.ComponentModel.EventHandlerList+ListEntry -- next System.ComponentModel.EventHandlerList+ListEntry -- next System.ComponentModel.EventHandlerList -- head PTU.MdiPTU -- (this as Component).events <-- The base application 

任何人都对我可能想要的东西有任何见解? 我发现在基本应用程序中添加了一个Shown事件,并确保在处理表单时将其删除,但这似乎没有解决问题。

非常感谢您提供的任何帮助。

后来编辑:我以为我已经好几次成功地解决了这个问题,而且我还有问题。 问题似乎源于我的Plotter类(和各种派生类)具有这个“公共静态事件MouseEventHandler MultiCursorMouseMove;” 事件。 我们有一个“光标”,显示图形在鼠标位置的值和时间。 最初,这一次在一个图表上工作,但是请求允许用户切换一种模式,其中移动鼠标将图表移动到所有显示的图形上。 当项目被实例化时,我写了一个初始处理程序挂钩EventHandlers,并且我在池塘的伙伴重新编写它以使用静态事件,该事件被分配给构造中的每个项目。 他的方式更优雅,效果更好。 除了导致内存泄漏之外的所有内容。 使用内存分析软件已经表明,每次我试图摆脱持有图的表格时,我都会留下一些“带有直接EventHandler根的Disposed实例”。 在每一个中,它表明对象是绘图仪或绘图仪指向的对象。 并且,在每个中,基本链接是MultiCursorMouseMove EventList指向这些对象。 我认为正在发生的事情是绘图仪是活着的,因为它有这个静态事件,而这个事件又与绘图仪有关。 我已经设法通过我的Dispose代码删除每个Plotter的事件来validationMultiCursorMouseMove在给定点通过调试器是空的,但是在同一点运行探查器仍然显示从MultiCursorMouseMove到这些类的链。

我目前没有关于如何解决这个问题的想法。 任何人?

如果MdiPTU是您的应用程序的MDI父表单,则听起来FormOpenWatch可能已订阅其中一个事件。 如果没有直接这样做,您可能会在FormOpenWatch超类中找到订阅,或者甚至可能在其他代码中找到可以从MdiPTU事件中连接FormOpenWatch方法的执行。