2009-08-07 34 views
15

我有一個線程運行,委託出一些任務。當一項任務完成時,會引發一個事件,說明它已完成。這些任務需要按照特定的順序運行,並且需要等待上一個任務完成。如何讓線程等待,直到它收到「任務完成」事件? (除了顯而易見的事件處理程序設置了一個標誌,然後一個while循環輪詢該標誌)可以使用哪些方法使線程等待事件並繼續執行?

回答

27

我經常使用的AutoResetEvent等待句柄,當我需要等待異步任務完成:

public void PerformAsyncTasks() 
{ 
    SomeClass someObj = new SomeClass() 
    AutoResetEvent waitHandle = new AutoResetEvent(false); 
    // create and attach event handler for the "Completed" event 
    EventHandler eventHandler = delegate(object sender, EventArgs e) 
    { 
     waitHandle.Set(); // signal that the finished event was raised 
    } 
    someObj.TaskCompleted += eventHandler; 

    // call the async method 
    someObj.PerformFirstTaskAsync();  
    // Wait until the event handler is invoked 
    waitHandle.WaitOne(); 
    // the completed event has been raised, go on with the next one 
    someObj.PerformSecondTaskAsync(); 
    waitHandle.WaitOne(); 
    // ...and so on 
} 
+1

根據第一個答案,我正在做一些與此非常相似的事情。使用EventResetMode.AutoReset初始化AutoResetEvent和EventWaitHandle有什麼區別? – MGSoto 2009-08-07 18:38:04

+0

@MGoto:我認爲差異很小(如果有的話):'AutoResetEvent'繼承自'EventWaitHandle',並且似乎使用其基類的構造函數向其傳遞'EventResetMode.AutoReset'。 – 2009-08-07 18:51:28

+2

別忘了,AutoResetEvent,WaitHandles等實現了IDisposable – 2013-06-17 14:03:10

5

一個選項是使用EventWaitHandle來表示完成。

+0

能否詳細說明一下?更好地解釋這一點,我會絕對投票! – Firoso 2009-08-07 17:58:53

+1

+1。 @firoso在msdn文章中有很多細節。 – 2009-08-07 18:18:03

+0

包含多種語言的示例 – bdonlan 2009-08-07 18:19:03

1

你可以使用這個ManualResetEvent

需要首先處理的線程只需要resetEvent,並等待直到結束才能設置事件。

需要等待的線程可以持有它的句柄,並調用resetEvent.WaitOne()。這將阻止該線程,直到第一個完成。

這允許您以非常乾淨的方式處理事件的阻塞和排序。

0

通過使用工作線程完成時調用的回調方法,我得到了很好的結果。它擊敗了輪詢,並且很容易將參數傳回給調用者。

相關問題