BackgroundWorker和ReportProgress冻结UI

时间:2012-10-06 16:00:11

标签: backgroundworker

我使用BackgroundWorker加载大文件。根据所选文件,它只能有4000行或400,000行。列数也各不相同。

我想逐步但快速地批量添加行。我改变了组成批次的行数。我的问题是第一批行被添加到FlexGrid中。如果文件足够大,需要添加第二批,则网格的滚动条跳汰机和屏幕会冻结。

我在按钮单击方法中调用RunWorderAsync方法来选择文件。我还将FlexGrid分配给数据表作为其数据源。

代码如下:

                //bind the grid to the empty table
                c1FlexGrid1.DataSource = dt;

                // go load the data
                backgroundWorker1.RunWorkerAsync(lengthOfFile);

FlexGrid来自ComponentOne,用于WinForms。

DoWorker代码如下:

// create rows for data table
    using (StreamReader streamRead = new StreamReader(filePathAndName))
        while ((lineOfData = streamRead.ReadLine()) != null)
        {
            rowCount++;
            sizeOfLine += lineOfData.Length;
            //create a new row in the data table
            var row = dt.NewRow();
            arrayOfData = lineOfData.Split(',');

            for (int j = 0; j < dt.Columns.Count; j++)
            {
                row[j] = arrayOfData[j];
            }
            newRowData.Add(row);

            percentComplete += 10;
            // inform progress at every 10 percent
            currentPercentComplete = ((double)sizeOfLine / sizeOfFile) * 100;
            if(((int)currentPercentComplete > percentComplete) && (percentComplete < 100))
            {
                Console.WriteLine("Starting UI thread - row count {0}, percent complete {1}, current percent {2}", rowCount, percentComplete, currentPercentComplete);
                percentComplete += 10;
                backgroundWorker1.ReportProgress(percentComplete);

                // simulate lengthy operation
                System.Threading.Thread.Sleep(1000);
            }

        }//end while loop

    }//end of using 

}

ProgressChanged方法如下:

    private void backgroundWorker1_ProgressChanged(object sender, ProgressChangedEventArgs e)
    {

        dt.BeginLoadData();
        for (int i = 0; i < newRowData.Count; i++)
        {
            dt.Rows.Add(newRowData[i]);
        }
        dt.EndLoadData();

//        Console.WriteLine("In UI thread ProgressChanged - end load -rows added - {0}", newRowData.Count);

        // done with this batch
        newRowData.Clear();

        // update UI
        this.progressBar1.Value = e.ProgressPercentage;
        Application.DoEvents();
    }

0 个答案:

没有答案