2017-02-16 104 views
2

我有這樣的代碼做什麼,我想:等待一個結果,而不阻塞線程

 TriggerSomeExternalProcess(); 
     double secondsElapsed = 0; 
     DateTime startTime = DateTime.UtcNow; 
     double timeoutInSeconds = 10; 
     while (secondsElapsed < timeoutInSeconds) { 
      // TODO: this seems bad... 
      secondsElapsed = DateTime.UtcNow.Subtract(startTime).TotalSeconds; 
     } 
     CheckStatusOfExternalProcess(); 

目標是TriggerSomeExternalProcess然後CheckStatusOfSomeExternalProcess - 但過程相同的線程上運行,所以我不能做Thread.Sleep()。這是一個不能等待的持續過程。

我覺得上面的while循環是錯誤的 - 當你需要等待而不會阻塞你的線程時,你採用什麼模式?

從其中一個答案的評論複製粘貼 不幸的是我無法觸及ExternalProcess中的代碼。我正在寫一個測試,這些是我可以訪問的方法。我知道這是不理想的

+0

可能的複製[異步等待任務以超時完成](http://stackoverflow.com/questions/4238345/asynchronously-wait-for-taskt-to-complete-with-timeout) –

+0

正在使用Timer選項嗎? –

+0

@PeterBons我想是這樣的......我現在要做一些研究如何在這種情況下使用它。 – SB2055

回答

2

而不是使用CheckStatusOfExternalProcess()方法你可能能夠將一個StatusChangedEvent添加到ExternalProcess東西,並附加一個EventHandler。這樣,當狀態發生變化時,您的事件處理程序就會被調用。

這是你的可能嗎?

順便說一句:如果你的兩個進程在同一個線程上運行 - 那怎麼能不被阻塞?

+1

感謝Tobias--不幸的是我無法觸及ExternalProcess中的代碼。我正在寫一個測試,這些是我可以訪問的方法。我知道這不太理想:p – SB2055

+0

哦,那肯定會感覺糟糕。如果我有另一個想法,我會告訴你;) –

+0

@ SB2055你應該把這條信息放到你的問題中,這是非常重要的 – NSGaga

0

我假定外部的過程不是您自己的過程。 因此它不能採取回調行動。 它不能發出心跳(定期發回它的當前狀態)。 它不能訂閱它的狀態改變。 這些將是處理它的正常方法。

在這種情況下,你可以只使用這樣的事情

Task.delay(TimeSpan.FromSeconds(10))).ContinueWith(() => CheckStatusOfExternalProcess()) 

繼續將立即啓用的第一個任務已完成,但現在你可以在你的代碼繼續,而不必擔心它

+0

:)因爲總是告訴我是什麼讓你失望,所以我可以避免它在未來。 –

+0

僅供參考我沒有downvote ... – SB2055

+0

爲什麼你需要一個'StartNew'在這裏?你可以簡單地'等待Task.Delay()。ContinueWith(...)',而不是添加太多的iverhead。 – VMAtm