2013-07-25 44 views
1

我在寫一個WinForm應用程序時填充我的組合框有問題。我用來填充這些組合框的數據是從數據庫中提取的。問題是有很多數據需要綁定到comboBoxes上,所以這個過程需要很長時間才能鎖定整個應用程序(綁定數據的整個過程需要9秒鐘的時間,而從數據庫中提取數據只需要400毫秒)。我試圖通過拆分創建控件(主線程)和填充comboBoxes(後臺工作者)的過程來加快速度,但自然我得到了交叉線程錯誤。 這是代碼的一部分,我用:設置來自backgroundWorker C#中的ComboBox DataSource

private void Populate() 
    {         
     comboBox1.BindingContext = new System.Windows.Forms.BindingContext(); 
     comboBox1.DataSource = MyClass.dtMyDataTable; 
     comboBox1.DisplayMember = "TitleColumn"; 

     .//I repeat the same code for each comboBox 
     .//I use the BiningContext because some of the comboBoxes have to display the 
     .//same data.    
    } 

我創建了一個包含我需要這種形式的所有數據表一類 - 有從數據庫中使用相同的數據多種形式,所以我創建了一個類,並創建一個對象,填充父Form.Load()上的所有這些DataTable,然後在創建它們時將它們傳遞給子表單。通過這種方式我可以在應用程序加載時加載數據(它甚至不需要那麼長時間),因此當我從子窗體調用它時應該可以使用。我試圖從backgroundWorker.DoWork()方法調用Populate()方法,在那裏我得到了交叉線程錯誤。

我的問題是 - 有沒有辦法使這項工作,如果沒有,我可以使用什麼作爲替代解決方案。

謝謝

+1

您需要使用'Control.BeginInvoke'或'Control.Invoke',它可以有效地將工作重定向到主線程。在這種情況下,它直接在主線程中調用'Populate'。 –

+2

您可以將加載移動到線程,但不是實際的數據綁定。從'backgroundWorker.Completed()'調用填充,而不是'.DoWork()' –

+0

@AlexFarber填充,你可以顯示這樣做的代碼。另外,如果我將Populate方法重定向到主線程(我在ChildForm.Load方法中調用該方法時解決方案的工作正常,但速度很慢),是否會失敗加速數據綁定過程的目的? – NDraskovic

回答

-1

我發現了一個很好的選擇,它從9秒加速到1.5秒。解決方法是在'comboBox.DataSource'行之前放置comboBox.DisplayMember,因爲當您更改DisplayMember(或ValueMember)時,數據源會自行重新填充。因此,如果comboBox.DisplayMember在'comboBox.DataSource'行之後,數據源會自行填充2次(我認爲在綁定數據源時默認啓用ClearBeforeFill,這就是綁定數據中沒有重複項的原因)。

無論如何。

0

我不是一個完整的瓶子上調用,但試試這個:

PopulateData() 
{ 
    if (combobox1.InvokeRequired) 
    { 
     combobox1.Invoke(new EventHandler(delegate(object o, EventArgs a) 
      { 
       PopulateData(); 
      } 
       )); 
    } 
    else 
    { 
     // Do your updates here... 
    } 
} 

我相信這將發現線程負責對於ComboBox,這將是在同一個線程其他組合的,然後運行。

我確定有人會用更好的方式來調用,也許在表單級調用?

+0

我試過這個,它可以工作,但是如果我從主線程調用它,它的速度就會很慢,所以它不是解決方案。 – NDraskovic

相關問題