C# 如何在catch块内处理InvalidOperationException

C# 如何在catch块内处理InvalidOperationException,c#,exception,asynchronous,try-catch,backgroundworker,C#,Exception,Asynchronous,Try Catch,Backgroundworker,我的代码使用BackgroundWorker从excel工作表中读取信息并将其上载到数据库,同时还显示一个通知用户进度的表单。这是一个C#项目 但是,在我读取excel文件并上传它们的try/catch语句中,我希望能够关闭进度表单,因为它不再有用了 当我调用BackgroundWorker类的.Close()方法时,会触发InvalidOperationException,我不确定如何处理这种情况。有办法处理吗?还有别的办法关窗户吗 这是我的catch块(位于DoWork事件中): backg

我的代码使用BackgroundWorker从excel工作表中读取信息并将其上载到数据库,同时还显示一个通知用户进度的表单。这是一个C#项目

但是,在我读取excel文件并上传它们的try/catch语句中,我希望能够关闭进度表单,因为它不再有用了

当我调用BackgroundWorker类的.Close()方法时,会触发InvalidOperationException,我不确定如何处理这种情况。有办法处理吗?还有别的办法关窗户吗

这是我的catch块(位于
DoWork
事件中):

backgroundWorker1是读取/上载数据的BackgroundWorker,progress是显示进度条和计数已完成/剩余信息的窗口

例外情况:

System.Windows.Forms.dll中发生“System.InvalidOperationException”类型的异常,但未在用户代码中处理其他信息:跨线程操作无效:控件“ProgressForm”是从创建它的线程以外的线程访问的


DoWork
事件中,您不能执行任何直接触及UI线程的操作,包括关闭(我假设)在运行线程之前创建的表单。这里有一个基本的“流程”供您遵循:

  • 创建进度表单的新实例并显示它

  • 启动后台工作人员

  • 不要在
    DoWork
    事件中捕获异常,除非您打算立即纠正导致异常的情况。否则,异常将停止工作线程,并导致
    RunWorkerCompleted
    事件,该事件将在UI线程上再次发生

  • 检查
    RunWorkerCompleted
    事件中的
    e.Error
    。。。如果它不是
    null
    ,则会出现异常,您可以采取适当的操作,例如通知用户。由于此事件已返回UI线程,因此您还可以关闭表单

  • 试一试:(动态编写,需要进行一些调整)


    是的,格兰特。我不知道为什么有人指责我没有阅读异常,或者为什么有人只是为了告诉我需要修复错误而发表评论。很明显,我是这样想的,但我无法弄清楚这就是我来这里的原因。异常内容为“System.Windows.Forms.dll中发生了“System.InvalidOperationException”类型的异常,但未在用户代码中处理其他信息:跨线程操作无效:控件“ProgressForm”是从创建它的线程以外的线程访问的。”因此,可能我无法调用.Close()在backgroundWorker1方法中?应该在哪里?让自己熟悉UI线程和后台线程之间的区别。在进行GUI编程时,必须了解这一点。这应该会让你开始。肯定有一些宝贵的资源在那里,谢谢。我只做了几个月的C#编程,这是我的第一个线程项目。简单的初学者的错误,所以我感谢你的输入。谢谢你的解释。它帮助我发现抛出的异常(我是特意为了测试而抛出的)可以在其他地方处理,并反过来改进了我的代码,因为我能够从一个excel文件移动到下一个excel文件,即使第一个excel文件不起作用。我知道,Try/Catch块很糟糕,但对于IO来说,它通常是最好的选择。无论如何,谢谢你的帮助!
    catch (Exception ex)
    {
        MessageBox.Show("Error Uploading Data. See log for details.", "Database Submission Error", MessageBoxButtons.OK);
        // Cancel operation
        backgroundWorker1.CancelAsync();
        // Close form
        progress.Close();
    }
    
    var progress = new MyProgressForm();
    progress.Show();
    
    backgroundWorker1.RunWorkerAsync();
    
    ...
    ...
    
    private void backgroundWorker1_RunWorkerCompleted(object sender, RunWorkerCompletedEventArgs e)
    {
        if (e.Error != null)
        {
            // log the exception
    
            MessageBox.Show("Error Uploading Data. See log for details.",
                            "Database Submission Error", MessageBoxButtons.OK);
    
            // we're back on the UI thread, so we can touch UI elements
            progress.Close();
    
            return;
        }
    
        // stuff to do if no error occurred
        ...
    }