2013-10-12 37 views
0

我該如何獲得ContinueWith等待兩個任務完成而不是一個?任務繼續帶事件鏈序列

我想確定如何將一組Task鏈接在一起,並讓一個接一個接着幾個鏈接級別。我有三個級別的鏈接。在第一級,我有一項任務。我想在第二級開始之前完成最高級別。在第二級,我有3個任務。我想在三級任務開始前完成三項任務中的兩項。


TopLevel > SecondLevel A \ ThirdLevel 
      SecondLevel B/
      SecondLevel C - Don't wait for this one for the third level 

我寫了下面的示例程序來測試如何做到這一點的工作方式如下

class Program 
{ 
    private static Random rand = new Random(); 
    public static Random Rand { get { return rand; } } 
    static void Main(string[] args) 
    { 

     Task topLevelTask = new Task(() => DoSomeWork("topLevelTask")); 
     Task secondLevelTaskA = topLevelTask.ContinueWith((task) => DoSomeWork("secondLevelTaskA"), TaskContinuationOptions.AttachedToParent); 
     Task secondLevelTaskB = topLevelTask.ContinueWith((task) => DoSomeWork("secondLevelTaskB"), TaskContinuationOptions.AttachedToParent); 
     Task secondLevelTaskC = topLevelTask.ContinueWith((task) => DoSomeWork("secondLevelTaskC"), TaskContinuationOptions.AttachedToParent); 
     Task thirdLevelTask = secondLevelTaskA.ContinueWith((task) => DoSomeWork("thirdLevelTask"), TaskContinuationOptions.AttachedToParent); 

     topLevelTask.Start(); 
     Console.ReadLine(); 
    } 

    private static void DoSomeWork(string task) 
    { 
     int sleep = Rand.Next(10000); 
     Console.WriteLine("Thread {0}: Ticks {1}: Task {2}: Sleep: {3}", Thread.CurrentThread.ManagedThreadId, DateTime.Now, task, sleep); 
     Thread.Sleep(sleep); 
     Console.WriteLine("Complete Task {0}", task); 
    } 
} 

對於這個不正是我想要的大部分。它啓動第一個任務並等待它完成,並行啓動3個二級任務。但是,我無法弄清楚如何設置第三級來等待taskA和taskB,因爲ContinueWith設置了單個父任務。

我曾嘗試將ContinueWith用於taskA和taskB上的第三級任務,但之後它運行了兩次。任何幫助,將不勝感激。這是我的示例程序的輸出。

Program Output

+0

http://stackoverflow.com/help/privileges/vote-down – Harrison

回答

4

您正在尋找ContinueWhenAll()

Task thirdLevelTask = Task.Factory.ContinueWhenAll(
    new[] { secondLevelTaskA, secondLevelTaskB }, 
    tasks => DoSomeWork("thirdLevelTask"), 
    TaskContinuationOptions.AttachedToParent); 

這樣做的優勢是Task.WhenAll().ContinueWith(),它會在.NET 4.0工作了。如果你使用.Net 4.5,使用async - await而不是ContinueWith()可能會更好。

0

我想通了。如果我更換

Task thirdLevelTask = secondLevelTaskA.ContinueWith((task) => DoSomeWork("thirdLevelTask"), TaskContinuationOptions.AttachedToParent); 

Task thirdLevelTask = Task.WhenAll(secondLevelTaskA,secondLevelTaskB).ContinueWith((task) => DoSomeWork("thirdLevelTask"), TaskContinuationOptions.AttachedToParent); 

它會做我想做的。這是新的輸出。

enter image description here