C# 按完成顺序对任务进行排序

C# 按完成顺序对任务进行排序,c#,asynchronous,task-parallel-library,C#,Asynchronous,Task Parallel Library,大约一年前,我看到乔恩·斯基特(Jon Skeet)在一次演讲中展示了一段C5代码,其中包含一个任务列表,并按完成的顺序返回任务 它使用了async/await和Wheny,非常漂亮,但我一辈子都记不起它是如何工作的。现在我需要它 我希望找出如何创建一个签名与此类似的方法 Task<IEnumerable<T>> InOrderOfCompletion<T>(IEnumerable<T> tasks) where T : Task 可按如下方式使

大约一年前,我看到乔恩·斯基特(Jon Skeet)在一次演讲中展示了一段C5代码,其中包含一个任务列表,并按完成的顺序返回任务

它使用了async/await和Wheny,非常漂亮,但我一辈子都记不起它是如何工作的。现在我需要它

我希望找出如何创建一个签名与此类似的方法

Task<IEnumerable<T>> InOrderOfCompletion<T>(IEnumerable<T> tasks) where T : Task
可按如下方式使用:

public async Task<int> DelayedInt(int i)
{
    await Task.Delay(i*100);
    return i;
}

[Test]
public async void Test()
{
    Task<int>[] tasks = new[] {5, 7, 1, 3, 2, 6, 4}.Select(DelayedInt).ToArray();
    IEnumerable<Task<int>> ordered = await InOrderOfCompletion(tasks);

    Assert.That(ordered.Select(t => t.Result).ToArray(), Is.EqualTo(new [] {1,2,3,4,5,6,7}));
}
我想到了以下几点,但感觉不像我记得的那么简单

    async Task<IEnumerable<T>> InOrderOfCompletion<T>(IEnumerable<T> tasks) where T : Task
    {
        HashSet<Task> taskSet = new HashSet<Task>(tasks);
        List<T> results = new List<T>();
        while(taskSet.Count > 0)
        {
            T complete = (T) await Task.WhenAny(taskSet);
            taskSet.Remove(complete);
            results.Add(complete);
        }
        return results;
    }
有人记得我提到的代码片段吗,或者如何改进它吗?

,所有的方法都略有不同。我的是如果你不想写你自己的


实际上,关键是要避免任务。因为这会使算法从ON变成ON^2。

谢谢,这正是我想要的,非常聪明的东西。