首页 >后端开发 >C++ >关闭Windows表单时,如何安全地停止背景工作者?

关闭Windows表单时,如何安全地停止背景工作者?

Barbara Streisand
Barbara Streisand原创
2025-01-31 17:06:12663浏览

How to Safely Stop a BackgroundWorker When Closing a Windows Form?

优雅地处理Windows窗体关闭时的后台工作线程

在Windows窗体中使用BackgroundWorker时,一个常见问题是在窗体关闭时停止工作线程。然而,在窗体关闭事件处理程序中简单地调用bgWorker.CancelAsync()可能会导致异常或死锁。

问题一:Invoke调用中的ObjectDisposedException异常

如果在窗体关闭事件处理程序中直接调用bgWorker.CancelAsync(),随后的Invoke调用可能会抛出ObjectDisposedException异常。这是因为窗体正在被释放,主线程已经退出。

问题二:bgWorker完成时的死锁

在窗体关闭事件处理程序中等待bgWorker完成可能会导致死锁,因为Invoke调用仍在进行中,阻止工作线程完成。

解决方法:协调窗体关闭和后台工作线程完成

为了解决这些问题,需要一种更稳健的方法:

  1. 在窗体关闭事件处理程序中,如果bgWorker仍在运行,则设置e.Cancel = true
  2. 设置一个标志closePending,指示用户请求关闭。
  3. bgWorkerRunWorkerCompleted事件处理程序中,检查closePending标志。如果已设置,则在窗体上调用Close()
<code class="language-csharp">private bool closePending;

protected override void OnFormClosing(FormClosingEventArgs e) {
    if (backgroundWorker1.IsBusy) {
        closePending = true;
        backgroundWorker1.CancelAsync();
        e.Cancel = true;
        this.Enabled = false;   // 或 this.Hide()
        return;
    }
    base.OnFormClosing(e);
}

void backgroundWorker1_RunWorkerCompleted(object sender, RunWorkerCompletedEventArgs e) {
    if (closePending) this.Close();
    closePending = false;
    // 其他操作...
}</code>

这种方法通过安全地处理窗体关闭事件和bgWorker的完成来防止异常和死锁。

以上是关闭Windows表单时,如何安全地停止背景工作者?的详细内容。更多信息请关注PHP中文网其他相关文章!

声明:
本文内容由网友自发贡献,版权归原作者所有,本站不承担相应法律责任。如您发现有涉嫌抄袭侵权的内容,请联系admin@php.cn