我想停止正在运行的线程并立即启动一个新线程而无需等待。 我的线程从数据库中读取并在UI中显示(计算后)结果。 如果用户单击按钮我需要"重启"与其他参数的线程。所以我必须停止正在运行的线程(不等待)并重新启动它。 这是一个简单的例子:
Dim mythread As Threading.Thread = Nothing
Dim mythreadCancel As Boolean = False
Private Sub Button3_Click(sender As Object, e As EventArgs) Handles Button3.Click
Try
If Not mythread Is Nothing Then
If mythread.IsAlive Then
mythreadCancel = True
End If
End If
mythread = New Threading.Thread(AddressOf threadRunning)
mythreadCancel = False 'if i set this here, the other thread is not stopping!
mythread.Start()
Catch ex As Exception
MsgBox(ex.Message)
End Try
End Sub
Private Sub threadRunning()
Try
While True
'long operation on Database
Threading.Thread.Sleep(10000)
If mythreadCancel = True Then
Exit Sub
End If
'ui operation (if not canceled)
'....
End While
Catch ex As Exception
MsgBox(ex.Message)
End Try
End Sub
Private Sub BtnStop_Click(sender As Object, e As EventArgs) Handles BtnStop.Click
mythreadCancel = True
End Sub
如果我设置了取消线程的标志,我需要将其设置回来,如果我启动下一个线程。 我怎样才能给正在运行的线程一个标志来中止?
我也使用过thread.abort。工作正常,但现在我已经读过,我永远不应该这样做。
[编辑]
感谢您的评论。我现在发现使用令牌。 我需要与STA的线程。它也适用于任务。但STA更复杂。
Dim tokenSource As New CancellationTokenSource()
Private Sub Button5_Click(sender As Object, e As EventArgs) Handles Button5.Click
Try
tokenSource.Cancel()
tokenSource = New CancellationTokenSource()
Dim mythread As New Threading.Thread(AddressOf ThreadRunning)
mythread.SetApartmentState(ApartmentState.STA)
mythread.Start(tokenSource.Token)
Catch ex As Exception
MsgBox(ex.Message)
End Try
End Sub
Private Sub ThreadRunning(ByVal obj As Object)
Try
Dim token As CancellationToken = CType(obj, CancellationToken)
Debug.WriteLine("Task starting")
While True
'long operation on Database
Threading.Thread.Sleep(1000)
If token.IsCancellationRequested Then
Debug.WriteLine("Exit Task")
Exit Sub
Else
Debug.WriteLine("Task running")
End If
'ui operation (if not canceled)
'....
End While
Catch ex As Exception
MsgBox(ex.Message)
End Try
End Sub
这似乎工作正常。这是正确的方法吗?
[/编辑]