我有一个listview循环,它将150,000个项目添加到我的列表视图中.出于测试目的,我将此代码移动到具有委托的后台工作者,但它仍然冻结了UI.我正在尝试找到一个解决方案,以便在我在应用程序中执行其他操作时可以在后台添加这些项目.你们推荐什么解决方案?
这就是我正在使用的
Public Class Form1 Private Sub Button1_Click(sender As Object,e As EventArgs) Handles Button1.Click ListView1.Clear() ListView1.BeginUpdate() bw.WorkerReportsProgress = True bw.RunWorkerAsync() End Sub Private Sub Button2_Click(sender As Object,e As EventArgs) Handles Button2.Click If bw.IsBusy Then bw.CancelAsync() End Sub Private Sub bw_DoWork(ByVal sender As Object,ByVal e As System.ComponentModel.DoWorkEventArgs) Handles bw.DoWork For x = 1 To 125000 Dim lvi As New ListViewItem("Item " & x) If bw.CancellationPending Then e.Cancel = True Exit For Else bw.ReportProgress(0,lvi) End If Next End Sub Private Sub bw_ProgressChanged(ByVal sender As Object,ByVal e As System.ComponentModel.ProgressChangedEventArgs) Handles bw.ProgressChanged Try Dim lvi As ListViewItem = DirectCast(e.UserState,ListViewItem) Me.ListView1.Items.Add(lvi) Catch ex As Exception Throw New Exception(ex.Message) End Try End Sub Private Sub bw_RunWorkerCompleted(ByVal sender As Object,ByVal e As System.ComponentModel.RunWorkerCompletedEventArgs) Handles bw.RunWorkerCompleted ListView1.EndUpdate() If Not e.Cancelled Then Debug.Print("Done") Else Debug.Print("Cancelled") End If End Sub End Class
尝试一下,这是你需要的一个很好的例子……我还有一个显示进度的进度条,参见示例图像.此外,我没有看到任何代表你需要执行这样的操作,我有一个将需要.原因是你正在向UI线程上的控件添加项目,以便添加我们需要知道的项目是否需要Invoke,如果是这样我们调用否则我们将项目添加到控件…另外我做了线程睡觉,所以可以休息一下;这也可以防止用户界面在这里和那里锁定,现在它响应没有冻结.
Option Strict On Option Explicit On Public Class Form1 Delegate Sub SetListItem(ByVal lstItem As ListViewItem) 'Your delegate.. 'Start the process... Private Sub btnStartProcess_Click(sender As Object,e As EventArgs) Handles btnStartProcess.Click lvItems.Clear() bwList.RunWorkerAsync() End Sub Private Sub AddListItem(ByVal lstItem As ListViewItem) If Me.lvItems.Invokerequired Then 'Invoke if required... Dim d As New SetListItem(AddressOf AddListItem) 'Your delegate... Me.Invoke(d,New Object() {lstItem}) Else 'Otherwise,no invoke required... Me.lvItems.Items.Add(lstItem) End If End Sub Private Sub bwList_DoWork(sender As Object,e As System.ComponentModel.DoWorkEventArgs) Handles bwList.DoWork Dim intCount As Integer = CInt(txtCount.Text) Dim dblPercent As Integer = 100 Dim intComplete As Integer = 0 Dim li As ListViewItem = Nothing For i As Integer = 1 To CInt(txtCount.Text) If Not (bwList.CancellationPending) Then li = New ListViewItem li.Text = "Item " & i.ToString AddListItem(li) Threading.Thread.Sleep(1) 'Give the thread a very..very short break... ElseIf (bwList.CancellationPending) Then e.Cancel = True Exit For End If intComplete = CInt(CSng(i) / CSng(intCount) * 100) If intComplete < dblPercent Then bwList.ReportProgress(intComplete) End If If li IsNot Nothing Then li = Nothing End If Next End Sub Private Sub bwList_ProgressChanged(sender As Object,e As System.ComponentModel.ProgressChangedEventArgs) Handles bwList.ProgressChanged pbList.Value = e.ProgressPercentage End Sub Private Sub bwList_RunWorkerCompleted(sender As Object,e As System.ComponentModel.RunWorkerCompletedEventArgs) Handles bwList.RunWorkerCompleted If pbList.Value < 100 Then pbList.Value = 100 MessageBox.Show(lvItems.Items.Count.ToString & " items were added!") End Sub Private Sub btnStopWork_Click(sender As Object,e As EventArgs) Handles btnStopWork.Click bwList.CancelAsync() End Sub Private Sub btnRestart_Click(sender As Object,e As EventArgs) Handles btnRestart.Click pbList.Value = 0 lvItems.Items.Clear() txtCount.Text = String.Empty End Sub End Class
动作截图…