0

我知道 Thread.Abort() 并不安全,但我无法想象在以下情况下会导致什么:

Private threadLoadList As Thread

Private Sub LoadList(ByVal argument As Integer)

    Try
        Refresh_Grid(GET_DATA(argument), argument) 'Fills grid with data loaded from database
        Change_Cursor() 'Changes cursor to Cursor.Default
    Catch ex As ThreadAbortException
        'Do nothing
    Catch ex As Exception
        Error_log(ex.Message) ' Saves ex.Message in database
    End Try

End Sub

Private Sub SomeValueChanged(sender As Object, e As EventArgs) Handles Control.ValueChanged
    If Not threadLoadList Is Nothing Then
         If threadLoadList.IsAlive Then
              threadLoadList.Abort()
         End If
     End If
     Cursor = Cursors.WaitCursor
     threadLoadList = New Thread(AddressOf LoadList)
     threadLoadList.Start(1)
 End Sub

如您所见,用户可以更改某些值(组合框)并最终更改网格的内容。函数 GET_DATA() 大约需要 10 秒,因此用户可能会在刷新网格之前更改 Combobox 的值 - 这就是之前启动的线程被杀死的原因。

危险吗?如果是,您能否提出其他解决方案?


好的,我明白了 ;)。我尽量避免超时(在某些情况下查询执行低于 1 秒)它是更好的解决方案:

Private threadLoadList As Thread
Private Changed As Boolean = False

Private Sub LoadList(ByVal argument As Integer)

    Try
        Dim dt As DataTable = GET_DATA(argument)
        'Enter Monitor
        If Changed Then
            Return
        End IF
        'Exit Monitor
        Refresh_Grid(dt, argument) 'Fills grid with data loaded from database
        Change_Cursor() 'Changes cursor to Cursor.Default
        'Enter Monitor
            Changed = False
        'Exit Monitor
    Catch ex As ThreadAbortException
        'Do nothing
    Catch ex As Exception
        Error_log(ex.Message) ' Saves ex.Message in database
End Try

End Sub

Private Sub SomeValueChanged(sender As Object, e As EventArgs) Handles Control.ValueChanged
     'Enter Monitor
        Changed = True
     'Exit Monitor
     Cursor = Cursors.WaitCursor
     Dim t As Thread = New Thread(AddressOf LoadList)
     t.Start(1)
 End Sub
4

1 回答 1

1

首先,除非有额外的代码,否则Refresh_Grid我看不到它看起来像是您试图从 UI 线程以外的线程修改 UI 元素。这是一个很大的禁忌。UI 元素被设计为只能从 UI 线程访问,因此尝试在工作线程上修改一个元素将导致不可预知的行为。

关于您Thread.Abort对答案的使用,是的;有危险。好吧,从某种意义上说,这是很危险的,您的应用程序将抛出异​​常、损坏数据、崩溃、在时空中撕开一个洞等。中止线程可能会出现各种故障模式。最好的解决方案是使用协作终止协议而不是硬中止。有关有效方法的简要介绍,参阅我的回答。

于 2013-07-23T14:52:25.647 回答