【发布时间】:2019-01-21 20:01:34
【问题描述】:
我正在尝试在我的 vb.net 代码中实现 BackgroundWorker。我了解您无法从后台工作人员更新 UI。因为当我在 Backgroundworker.DoWork 子代码中设置断点时,我会得到 Me.Accessibility.Object 引发了“System.InvalidOperationException”类型的异常 消息“跨线程操作无效:控制 'FrmLoad' 从创建它的线程以外的线程访问。”
为了试图理解为什么会发生这种情况,我完全复制了代码 https://docs.microsoft.com/en-us/dotnet/api/system.componentmodel.backgroundworker?view=netframework-4.7.2 并且在 DoWork 子中再次设置断点时,我得到了同样的异常。我已经尝试了其他几个具有相同问题的微软代码示例。代码有问题吗?
Imports System
Imports System.ComponentModel
Imports System.Windows.Forms
Namespace BackgroundWorkerSimple
Public Partial Class Form1
Inherits Form
Public Sub New()
InitializeComponent()
backgroundWorker1.WorkerReportsProgress = True
backgroundWorker1.WorkerSupportsCancellation = True
End Sub
Private Sub startAsyncButton_Click(ByVal sender As Object, ByVal e As EventArgs)
If backgroundWorker1.IsBusy <> True Then
backgroundWorker1.RunWorkerAsync()
End If
End Sub
Private Sub cancelAsyncButton_Click(ByVal sender As Object, ByVal e As EventArgs)
If backgroundWorker1.WorkerSupportsCancellation = True Then
backgroundWorker1.CancelAsync()
End If
End Sub
Private Sub backgroundWorker1_DoWork(ByVal sender As Object, ByVal e As DoWorkEventArgs)
Dim worker As BackgroundWorker = TryCast(sender, BackgroundWorker)
For i As Integer = 1 To 10
If worker.CancellationPending = True Then
e.Cancel = True
Exit For
Else
System.Threading.Thread.Sleep(500)
worker.ReportProgress(i * 10)
End If
Next
End Sub
Private Sub backgroundWorker1_ProgressChanged(ByVal sender As Object, ByVal e As ProgressChangedEventArgs)
resultLabel.Text = (e.ProgressPercentage.ToString() & "%")
End Sub
Private Sub backgroundWorker1_RunWorkerCompleted(ByVal sender As Object, ByVal e As RunWorkerCompletedEventArgs)
If e.Cancelled = True Then
resultLabel.Text = "Canceled!"
ElseIf e.[Error] IsNot Nothing Then
resultLabel.Text = "Error: " & e.[Error].Message
Else
resultLabel.Text = "Done!"
End If
End Sub
End Class
End Namespace
它实际上并没有阻碍代码运行,但我想确保线程实际上保持安全。
【问题讨论】:
-
我无法使用此代码重现任何异常。无论我放置调试停止,它都会愉快地停止。
-
听起来您的项目或系统中的某些内容已损坏。我会尝试创建一个新项目并尽可能少地进行更改以尝试运行此代码。如果它仍然行为不端,请尽可能在另一台机器上尝试相同的操作。获取异常的堆栈跟踪也可能会有所帮助,这样您就可以准确地看到它发生的位置。
-
我之前忘了说 - 原始代码是 C#。我尝试为 C# 和 .Net 版本的 bot 构建一个新项目 - 仍然是同一个问题。我现在不能尝试另一台计算机,因为有许可证的同事不在。我确实尝试按照 jmoreno 的建议添加处理程序,并确保如 Michael Royston 所指出的那样包含 ProgressChanged 事件处理程序。还是没有变化。只是想解决这个问题。