内存泄漏问题

Jay*_*Pea 2 c# garbage-collection dispose idisposable

自从我被要求修复一个有内存泄漏问题的C#应用​​程序以来,我一直在阅读很多内容,但我没有找到这两个问题的答案:

请考虑以下代码:

   private static ArrayList list = new ArrayList();

   public void Function()
   {
     list.add(object1);
     list.add(object2);

     //didn't call clear() prior to reusing list
     list = new ArrayList();
   }
Run Code Online (Sandbox Code Playgroud)

由于列表在创建新列表之前未被清除,这是否会产生某种垃圾,在静态列表本身被释放后不会被释放?

第二个问题是关于Form.Dispose().我看到设计师视图(即标签,图片框)上的许多控件都需要处理.似乎在Form上调用Dispose()会导致所有这些类型的控件也被处理掉(如果我错了就纠正我),这很奇怪,因为设计师添加了一个覆盖的void Dispose(bool disposing)方法,没有这样的事.我假设这发生在基本Form类的void Dispose(bool disposing)方法中.

上面的问题是,我不清楚我需要做些什么才能确保正确处理所有Form的资源.我不明白Form如何知道它需要处理哪些对象.例如,如果在我的表单中我有一个自定义IDisposable对象的字段,表单是否知道它需要处理?或者我应该添加自己发布对象所需的代码?

另外,如果我确实需要添加代码来处理某些对象,那么我该如何处理设计者已经覆盖void Dispose(bool disposing)方法的事实呢?我应该编辑设计器生成的代码还是有更简洁的方法来执行此操作?

我希望这不要混淆,这有点难以解释.谢谢

Han*_*ant 8

不,那不是泄密.当垃圾收集器搜索对象引用时,它将不再找到对原始ArrayList的引用.你替换了它.因此,它会自动销毁原始的ArrayList对象,以及它们在任何地方都没有被引用的所有元素.

Form类知道如何处置自己,以及该窗体上的子窗口的所有控件.当用户关闭表单时会发生这种情况,Windows发送的WM_CLOSE消息会触发此代码.Form.Controls集合可帮助它找到对所有子控件的引用,以便它也可以处置它们.

但是,如果您自己从表单中删除控件,则不会发生这种情况.现在你可以在它们上面调用Dispose()了.特别是Controls.Clear()方法很危险.有什么不寻常之处在于它会导致永久性泄漏,你移除的控制装置会被"停车窗口"保持活着.这使窗口句柄保持活动状态,以便您可以将它们移动到其他容器窗口上,例如.如果你实际上没有移动它们,它们将永远保留在停车窗口上.框架中的其他类没有这种方式.

使用Taskmgr.exe,Processes选项卡可以轻松诊断此泄漏.查看+选择列并勾选用户对象.如果程序运行时这种情况稳步上升,那么你就会泄漏控件.