我正在制作一个简单的多线程程序来解释线程的工作原理。我想要两个计数器同时计数,但它不起作用。
它仅在我使用时才有效:CheckForIllegalCrossThreadCalls = False
。但是,我想以正确的方式编程。
Code:
Dim Thread1 As System.Threading.Thread
Dim Thread2 As System.Threading.Thread
Private Delegate Sub SetTeller1()
Private Sub teller1()
If teller1Label.InvokeRequired Then
Invoke(New SetTeller1(AddressOf teller1))
Else
For i As Integer = 0 To 1000
teller1Label.Text = i
Refresh()
Next
End If
End Sub
Delegate Sub SetTeller2()
Private Sub teller2()
If teller2Label.InvokeRequired Then
Invoke(New SetTeller2(AddressOf teller2))
Else
For i As Integer = 0 To 1000
teller2Label.Text = i
Refresh()
Next
End If
End Sub
Private Sub teller1Button_Click(sender As Object, e As EventArgs) Handles teller1Button.Click
Thread1 = New Threading.Thread(AddressOf teller1)
Thread1.Start()
End Sub
Private Sub teller2Button_Click(sender As Object, e As EventArgs) Handles teller2Button.Click
Thread2 = New Threading.Thread(AddressOf teller2)
Thread2.Start()
End Sub
多线程工作得很好,但你没有利用它。您当前在后台线程中做的唯一事情就是调用Invoke
,这意味着您的线程将在几毫秒内退出,然后被丢弃。
一旦你打电话Invoke
的执行teller1
or teller2
方法被移至 UI 线程,这意味着它将阻塞 UI,直到其执行完成。你应该只调用当你要更新 UI 时,并在后台线程中执行所有迭代。
以下是如何更正确地做到这一点的示例:
Delegate Sub SetTeller1(ByVal Text As String)
Private Sub teller1()
For i As Integer = 0 To 1000
SetTeller1Text(i)
Next
End Sub
Private Sub SetTeller1Text(ByVal Text As String)
If Me.InvokeRequired Then
Me.Invoke(New SetTeller1(AddressOf SetTeller1Text), Text)
Else
teller1Label.Text = Text
Me.Refresh()
End If
End Sub
为了提高可读性,我改变了例如Invoke(...)
to Me.Invoke(...)
.
我也不确定你为什么打电话Refresh()
因为它不是必需的,只会导致整个容器的额外重绘(猜测这是一种表单)。
本文内容由网友自发贡献,版权归原作者所有,本站不承担相应法律责任。如您发现有涉嫌抄袭侵权的内容,请联系:hwhale#tublm.com(使用前将#替换为@)