跨線程操作無效:從創建它的線程以外的線程訪問控制我有一個場景。(Windows Forms,C#,.NET)有一個主要表單托管一些用戶控件。用戶控件執行一些繁重的數據操作,這樣如果我直接調用該UserControl_Load方法,則UI在加載方法執行的持續時間內變得無響應。為了克服這個問題,我在不同的線程上加載數據(嘗試盡可能少地更改現有代碼)我使用了后臺工作線程來加載數據,完成后會通知應用程序已經完成了它的工作。現在來了一個真正的問題。所有UI(主窗體及其子用戶控件)都是在主要主線程上創建的。在usercontrol的LOAD方法中,我基于userControl上的某些控件(如文本框)的值來獲取數據。偽代碼看起來像這樣:代碼1UserContrl1_LoadDataMethod(){ if (textbox1.text == "MyName") // This gives exception { //Load data corresponding to "MyName". //Populate a globale variable List<string> which will be binded to grid at some later stage. }}它給出的例外是跨線程操作無效:從創建它的線程以外的線程訪問控制。為了更多地了解這一點,我做了一些谷歌搜索,并提出了一個建議,如使用下面的代碼代碼2UserContrl1_LoadDataMethod(){ if (InvokeRequired) // Line #1 { this.Invoke(new MethodInvoker(UserContrl1_LoadDataMethod)); return; } if (textbox1.text == "MyName") // Now it wont give an exception { //Load data correspondin to "MyName" //Populate a globale variable List<string> which will be binded to grid at some later stage }}但是但是......似乎我又回到原點了。應用程序再次無響應。這似乎是由于條件#1執行。加載任務再次由父線程完成,而不是我生成的第三個。我不知道我是否認為這是對還是錯。我是線程新手。如何解決這個問題以及阻止執行第1行的影響是什么?情況是這樣的:我想根據控件的值將數據加載到全局變量中。我不想從子線程更改控件的值。我不打算從子線程中做到這一點。因此只訪問該值,以便可以從數據庫中獲取相應的數據。
5 回答
手掌心
TA貢獻1942條經驗 獲得超3個贊
您只想使用Invoke或BeginInvoke來完成更改UI所需的最少工作量。你的“重”方法應該在另一個線程上執行(例如通過BackgroundWorker),然后使用Control.Invoke / Control.BeginInvoke來更新UI。這樣你的UI線程就可以自由處理UI事件等。
請參閱我的線程文章以獲取WinForms示例 - 雖然文章是在BackgroundWorker到達現場之前編寫的,但我擔心我沒有在這方面更新它。BackgroundWorker只是略微簡化了回調。
POPMUISE
TA貢獻1765條經驗 獲得超5個贊
我遇到了這個問題,FileSystemWatcher發現以下代碼解決了這個問題:
fsw.SynchronizingObject = this
然后,控件使用當前表單對象來處理事件,因此將在同一個線程上。
守著一只汪
TA貢獻1872條經驗 獲得超4個贊
我現在知道太晚了。但是,即使在今天,如果您在訪問跨線程控件時遇到問題?這是迄今為止最短的答案:P
Invoke(new Action(() =>
{
label1.Text = "WooHoo!!!";
}));這是我從線程訪問任何表單控件的方式。
- 5 回答
- 0 關注
- 848 瀏覽
添加回答
舉報
0/150
提交
取消
