事件是否保证会发生
本文关键字:是否 事件 | 更新日期: 2023-09-27 17:57:13
假设我有一个从Form继承的表单SomeForm。
public class SomeForm : Form
{
private void SomeForm_FormClosed(object sender, FormClosedEventArgs e)
{
MessageBox.Show("FormClosed event in SomeForm class");
}
}
public class Consumer
{
SomeForm someForm = new SomeForm();
someForm = null; //Ideally the messagebox would display here
SomeForm someForm = new SomeForm();
someForm.Close(); //Messagebox would display in this case as well
}
我想在窗体关闭时显示该消息框。 我应该把它贴在 FormClosed 事件中吗? 假设每次运行析构函数之类的内容时都会触发 FormClosed 事件是否安全? 有没有更好的位置来放置关闭表单时必须发生的代码?
编辑
有人在下面的评论中提出了一个很好的观点。 当类的实例设置为 null 时,事件似乎不会触发。 但是,当实例设置为 null 时,是否仍会调用析构函数或其他一些方法。 我想保证我的代码在用户完成类时运行。
我也知道,强制关闭系统、结束进程、天灾等无论如何都不会导致我的代码运行。 =)
是的,除非发生异常情况,例如通过系统命令杀死它或拔掉插头,否则将调用它。其他情况包括
- 将变量设置为
null
(不调用Close
方法) - 另一个委托中的异常:所有事件都
MulticastDelegate
s,并且委托按在该MulticastDelegate
中出现的顺序执行,如果前面的委托之一导致异常,则不会调用您的委托。
除非您的可执行文件被强制关闭(通过任务管理器或命令行
taskkill
)或程序崩溃,否则它将被调用。
编辑:我做了一些实验,发现了以下内容:
- 如果将对窗体的引用设置为 null,则窗体仍然可见,并且当窗体关闭时,将引发事件。 如果您的窗体是子窗体,
- 并且主窗体已关闭,则子窗体将关闭而不引发事件。
- 如果调用窗体的
Hide()
方法,则不会引发该事件。 如上所述,随后关闭主窗体不会导致引发事件。 - 重写
OnClosed()
无济于事,因为如果主窗体关闭,它仍然不会被调用。 - 调用表单的
Dispose()
方法(如果没有指向它的内容,GC 最终会这样做)也不会导致引发事件。
看起来真的没有办法保证代码将从表单中调用。 您可以将代码放在Application.Run();
之后Main()
,它就会在那里被调用。 还有一个Application.ApplicationExit
事件,除非您有特殊情况(强制关闭或崩溃),否则会被调用。
您可以在窗体中为 Application.ApplicationExit
事件注册处理程序,但请注意,此时您的对象已被释放,因此您无法对其进行任何操作。
FormClosed 事件由 OnClosed 方法引发。因此,如果您想要一定程度的保证,则可以覆盖OnClosed方法。