使用对话框周围的语句来确保垃圾收集
我们有一个包含数千个表单的 Windows 窗体应用程序。
其中许多通过 ShowDialog() 方法临时显示为对话框。
该应用程序已经存在多年,我们发现由于表单或其使用的控件中的各种资源泄漏,许多表单没有及时进行垃圾收集。
具体来说,我们发现了未正确处理 GDI+ 资源的示例,尽管可能还存在其他类型的资源泄漏尚未表征。
尽管解决这个问题的正确方法显然是通过每一种形式和每一种控制并消除所有资源问题。这需要一些时间才能完成。
作为短期替代方案,我们发现在表单上显式调用 Dispose() 似乎会启动垃圾收集过程,并且表单及其资源会立即释放。
我的问题是,将每个表单的 ShowDialog() 块包装在 using 语句中是否是一个合理的解决方法,以便在显示表单后调用 Dispose() ,并且这通常也是一个很好的实践吗?
例如,将现有代码从以下位置更改为:
public void ShowMyForm()
{
MyForm myForm = new MyForm();
myForm.ShowDialog();
}
在
public void ShowMyForm()
{
using (MyForm myForm = new MyForm())
{
myForm.ShowDialog();
}
}
我们的测试中,第一个示例永远不会调用 MyForm 的 Dispose() 方法,但第二个示例会立即调用它。
当我们花时间追踪每个特定资源问题时,作为短期解决方法,这似乎是一个合理的方法吗?
我们是否可以考虑其他方法作为短期解决方法和/或方法来识别和解决这些类型的资源问题?
We have a Windows Forms application that contains thousands of forms.
Many of these are temporarily displayed as dialogs via the ShowDialog() method.
This application has been around for years and we've discovered that many of the forms are not getting garbage collected in a timely manner due to various resource leaks in the form or the controls that it uses.
Specifically, we've found examples of GDI+ resources that aren't being disposed of properly, although there may be other types of resource leaks that have not yet been characterized.
Although the right way to resolve this is obviously to go through every form and every control and eliminate all of the resource problems. This will take some time to accomplish.
As an short term alternative, we have found that explicitly calling Dispose() on the form seems to initiate the garbage collection process and the form and its resources are deallocated immediately.
My question is whether is would be a reasonable workaround to wrap each form's ShowDialog() block in a using statement so that Dispose() is called after the form has been displayed, and also would this be a good practice to institute in general?
For example, change the existing code from this:
public void ShowMyForm()
{
MyForm myForm = new MyForm();
myForm.ShowDialog();
}
To this:
public void ShowMyForm()
{
using (MyForm myForm = new MyForm())
{
myForm.ShowDialog();
}
}
In our testing, MyForm's Dispose() method never gets called for the first example, but it gets called immediately for the second example.
Does this seem like a reasonable approach as a short term workaround while we spend the time tracking down each of the specific resource issues?
Are there other approaches that we could consider for a short term workaround and/or methodologies for identifying and resolving these types of resource issues?
如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。
绑定邮箱获取回复消息
由于您还没有绑定你的真实邮箱,如果其他用户或者作者回复了您的评论,将不能在第一时间通知您!
发布评论
评论(3)
根据 MSDN,您必须在使用 ShowDialog 显示的表单上显式调用 Dispose(与 Show 方法不同) ):
According to MSDN, you must explicitly call Dispose on forms shown using ShowDialog (unlike with the Show method):
对于模态对话框,您应该使用以下模式:
由于 MyDialog 派生自 Form,并且 Form 实现了 IDisposable,因此该模式将正确清理您的对话框。
这不应该是“短期解决方法”,而是您应该调用所有模式对话框的标准方法。
无模式对话框是另一回事。您需要自己跟踪它们,并在应用程序中的适当位置调用Dispose。
For modal dialogs, you should use the pattern:
Since MyDialog is derived from Form, and Form implements IDisposable, this pattern will correctly cleanup your dialog.
This should not be a "short term workaround", but the standard way you should invoke all your modal dialogs.
Modeless dialogs are another story. You would need to keep track of them yourself, and call Dispose at the appropriate points in your application.
一般来说,对于实现 IDisposable 的对象使用
using
语句是一个好方法。一个小示例情况:
假设您有一个第三方“组件”。你无法知道内部发生了什么
也许这个对象会创建一个临时文件并在
Dispose
上删除该文件。如果你不要调用
Dispose()
并且不要使用using
文件永远不会被删除。在您的情况下,只要打开表单
modal
,您也可以这样做。In general it is a good way to use the
using
statement for objects that implement IDisposable.A little sample situation:
Lets say you have a third party "component". You cant know what goes on internally
and maybe this objects creates a temp file and delete the file on
Dispose
. If youdont call
Dispose()
and dont useusing
the file will never get deleted.In your case you can do it too as long as you open your form
modal
.