2011-12-11 56 views
1

爲什麼下面的代碼在5秒後執行WebRequests時UI線程不再被阻塞? Thread.Sleep位於UI線程中,而WebRequest的實例化和調用都發生在ThreadPool的線程內。當UI線程被阻塞時在後臺線程中執行WebRequest

Loaded += (sender, args) => { 

    for (int i = 0; i < 5; i++) { 

     ThreadPool.QueueUserWorkItem(state => { 
      var request = WebRequest.CreateHttp("http://google.com"); 
      request.BeginGetResponse(ar => Debug.WriteLine("Request finished"), null); 
     }); 

     Thread.Sleep(1000); 
    } 

}; 

我應該寫什麼代碼才能在UI線程被阻塞時在後臺線程中執行WebRequest?

編輯: ...更具體。爲什麼這個請求在10秒後被執行,因爲它在後臺線程中?

Loaded += (sender, args) => { 

    ThreadPool.QueueUserWorkItem(state => { 
     var request = WebRequest.CreateHttp("http://google.com"); 
     request.BeginGetResponse(ar => Debug.WriteLine("Request finished"), null); 
    }); 
    Thread.Sleep(10000); 

}; 

回答

1

我問幾乎相同的問題在這裏(我將立即關閉,我發現你的): DownloadStringAsync requires UI thread?

答案是,所有的網絡代碼最終是編組到第5版之前的Silverlight中的UI線程。不幸的是,即使我針對Silverlight 5構建時,我仍然遇到同樣的問題,所以我仍在調查...

0

也許你的意思是要做到這一點,而不是:

Loaded += (sender, args) => 
{ 
    ThreadPool.QueueUserWorkItem(dummy => 
    { 
     for (int i = 0; i < 5; i++) 
     { 

      ThreadPool.QueueUserWorkItem(state => 
      { 
       var request = WebRequest.CreateHttp("http://google.com"); 
       request.BeginGetResponse(ar => Debug.WriteLine("Request finished"), null); 
      }); 

      Thread.Sleep(1000); 
     } 
    }); 

}; 

這完全不阻止用戶界面和調試的短信進入每一秒。或者你想要的行爲是什麼?你真的想阻止用戶界面(你不應該......)?

編輯(你的編輯後):

我明白了。這是一種反直覺,我沒有立即回答。我強烈懷疑這個請求需要一些UI線程活動。你的主線程應該始終是響應式的,永遠不要阻塞,所以這不成問題。除非你阻止主線程。所以他們可能會爲了這個有缺陷的情況而優化自己的工作(這是)。

不過,答案會很有趣。我從桌面世界知道,瀏覽器相關的東西需要主線程。因此,我建議不要阻止它了:)

+0

謝謝您的回答。我知道你的解決方案有效,但這不是我正在尋找的。請看我編輯的問題。 – djsolid

相關問題