为什么我在使用BackgroundWorker时遇到了巨大的性能提升.Dispatcher.BeginInvoke((Action)delegate()

时间:2015-10-06 16:56:09

标签: wpf multithreading backgroundworker begininvoke

我有一个从数据库导入数据并在WPF应用程序中填充DataGridView(winform)的函数。

最初我让应用程序通过它的主线程调用该函数。性能每1000行运行大约10秒,这比我想要的要长得多。但是,由于使用了这个应用程序并不需要多长时间,因此我并不担心提高速度。

我尝试做的是通过使用BackgroundWorker检索行来使行填充,然后调用BackgroundWorker在它们进入时添加行+提供进度条。

我正在摆弄并决定只调用整个方法,现在导入数据行的时间更像是每1000行1秒。

我的代码看起来像这样:

Window_Loaded() 
{
        dataPopulater = new BackgroundWorker(); // variable declared in the class
        dataPopulater.WorkerReportsProgress = true;
        dataPopulater.DoWork += new DoWorkEventHandler(dataPopulater_DoWorkReadSavedRecords);
        dataPopulater.ProgressChanged += new ProgressChangedEventHandler(dataPopulater_ProgressChanged);
        dataPopulater.RunWorkerCompleted += dataPopulater_RunWorkerCompleted;
        dataPopulater.RunWorkerAsync(startUpRead);
}

private void dataPopulater_DoWorkReadSavedRecords(object sender, DoWorkEventArgs e)
    {
        this.Dispatcher.BeginInvoke((Action)delegate()
            {
              //Import method...
            });
    }

有关为何我会获得如此高涨的表现的任何想法?我的理解是this.Dispatcher.BeginInvoke((Action)delegate(){});命令运行主线程后面的任何内容,这是我之前使用10sec / 1,000行性能执行的操作。是否正在创建一个BackgroundWorker来分配更多处理速度/核心或类似的东西?

我只是不知道为什么会这样。

1 个答案:

答案 0 :(得分:1)

根据您的评论,以前版本的代码是在更新循环中向datagrid添加一行。向网格控件添加一行会产生大量开销,主要来自控件重新绘制自身。

在表单上调用.BeginInvoke实际上并不立即执行工作,它只是将工作排队到UI线程并立即返回。这一小改动允许您的更新逻辑在与UI更新不同的线程上以全速​​运行。您基本上将逻辑与表示分开,允许每个逻辑彼此异步运行。