2017-04-21 67 views
0

在任何給定的時間,我的WPF應用程序有一堆異步Task在後臺線程/同步上下文中運行的S的。在關機時,我需要設置一個CancellationToken,然後等待這些任務完成正常之前,我可以開始拆除本機庫,他們依靠。但是,一些任務有延續的是(需要)在主線程上運行,因此在同一個線程死鎖會調用Task.WaitAll(_myTasks)。我想要做的是這樣的:等待任務在關機不完整的死鎖

while(!AreAllTasksComplete(_myTasks)) 
    LetContinuationsThatAreWaitingForThisContextRun(); 
TearDownTheNativeLibraries(); 

但當然LetContinuationsThatAreWaitingForThisContextRun的()不存在。有沒有辦法做我想做的事情?我需要一個完全不同的方法嗎?

+1

怎麼樣另一個後臺線程手錶您的任務,而你的主線程可以返回一個消息循環?也許是等待... – DarkSquirrel42

+0

它有一段時間的感覺,我不得不做很多任務,但你可能想看看Task.WhenAll。這個問題解釋一點關於它的uses.http://stackoverflow.com/questions/22699048/why-does-task-waitall-not-block-or-cause-a-deadlock-here – Hack

+0

由於這是一個WPF應用程序,事實證明我可以像這樣實現'LetContinuationsThatAaWaitingForThisContextRun()':Dispatcher.CurrentDispatcher.Invoke(()=> {},DispatcherProperity.Background')。這起作用(看似),但它依賴於可能沒有記錄的行爲。 – dlf

回答

0

你可以做

await Task.WhenAll(_myTasks); 
TearDownTheNativeLibraries(); 
+0

喜歡的東西,這是我的第一個想法,但我需要一種方法來阻止應用退出直到TearDownTheNativeLibraries延續後()運行。否則,在我等待時,shudown過程將繼續,應用程序將退出,並且TearDownTheNativeLibraries()永遠不會發生,從而導致它們管理的文件可能處於不一致的狀態。我可能最終會做這樣的事情,但這需要一些重構。 – dlf

+0

這取決於(一)什麼事件觸發關機(例如點擊按鈕)和(b)你如何指揮系統終止您(例如,在主窗口中調用close())。 – dvorn