2012-11-14 126 views
2

我正在編寫一個C#控制檯應用程序,並且在所有產生的關閉任務有機會完成之前主線程關閉時出現問題。一般程序流程如下所示:確保主線程等待所有任務完成

程序將指向目錄的路徑作爲命令行參數。然後,它遍歷該目錄中匹配特定擴展名的所有文件,併產生一個新的任務對每個匹配的文件打開和分析文件:

Directory.GetFiles(directoryPath).ToList<string>().Where(x => Path.GetExtension(x) == ".xfast").ToList().ForEach(x => ProcessXFastFile(x)); 

每個文件都包含對應回了大量的CSV值到一個獨特的產品密鑰。例如,一個文件可能包含1百萬個CSV行和400個唯一的產品密鑰。程序的要點是根據產品密鑰對所有行進行排序,並根據密鑰將其寫回單個文件。

因此,在ProcessXFastFile方法中,我創建一個Dictionary<string, List<string>>,使用產品代碼作爲鍵值並將每個與該鍵匹配的CSV行添加到相應的列表中。

一旦整理完畢,我遍歷字典和產卵掀起了新任務每個鍵值,並在該列表中寫出來的CSV行:

foreach (KeyValuePair<string, List<string>> entry in productDictionary) { 
    string writePath = String.Format(@"{0}\{1}-{2}.txt", directoryPath, hour, entry.Key); 
    List<string> quotes = entry.Value; 
    Task writeFileTask = Task.Factory.StartNew(() => WriteProductFile(writePath, quotes)); 
} 

的問題是,主線程是在WriteProductFile的每個任務都有機會完成寫出數據之前結束。例如,我使用一個文件作爲控制測試,並知道字典中有〜450個唯一鍵,因此應該有多個相應的文件被寫出。但是,在節目結束之前,只有大約10個文件有機會寫出來。

如何確保我的程序保持足夠長的時間,以便所有任務完成?任何幫助表示讚賞。

回答

5

你可以把所有的你進入一個List<Task>的任務,而不只是他們創造和折騰他們,然後用Task.WaitAll()等待完成:

var tasks = new List<Task>(); 

foreach (KeyValuePair<string, List<string>> entry in productDictionary) { 
    string writePath = String.Format(@"{0}\{1}-{2}.txt", directoryPath, hour, entry.Key); 
    List<string> quotes = entry.Value; 

    // add task to list 
    tasks.Add(Task.Factory.StartNew(() => WriteProductFile(writePath, quotes))); 
} 

// now wait for all tasks to finish, you'd also want to handle exceptions of course. 
Task.WaitAll(tasks.ToArray()); 

還有的WaitAll()很多變化,你可以無限期地等待(如上所述),或等待TimeSpan,如果超時然後打印進度信息並再次等待,等等...

+0

不錯,這看起來很有希望我現在就給它一個 –

+0

完美地工作。感謝您提供簡潔而簡單的解決方案! –

+0

沒問題!很高興我能幫上忙! –