简体   繁体   English

如何从第一个任务中获取结果然后在循环中使用 ContinueWith 将其传递给第二个任务?

[英]How to get result from 1st task then pass it to 2nd task using ContinueWith in a loop?

So here's what I'm doing:所以这就是我在做什么:

var resultObj = GetFirstResultAsync()
     .ContinueWith(t => GetSecondResultAsync(resultObj))
     .Wait();

Essentially telling me that I can't use the variable before it's even declared, which I get hence the question I posted.本质上告诉我,我什至不能在变量声明之前使用它,因此我得到了我发布的问题。 How do I do this?我该怎么做呢?

Here's my goal, I have a list resultObj then on that list I will loop through the Id's to get an array of my another list that I want GetSecondResultAsync kinda drilling down on the list, I wanted to use async since it will be using HttpClient to get the data.这是我的目标,我有一个列表resultObj然后在该列表上我将遍历 Id 以获取另一个列表的数组,我希望GetSecondResultAsync在列表上向下钻取,我想使用异步因为它将使用HttpClient来获取数据。

You should be able to pass the result by changing the ContinueWith statement to t.Result.您应该能够通过将 ContinueWith 语句更改为 t.Result 来传递结果。 Something like:就像是:

var resultObj = GetFirstResultAsync()
 .ContinueWith(t => GetSecondResultAsync(t.Result));

I haven't tested the code.我还没有测试代码。

The first run thread will return a "Task".第一个运行的线程将返回一个“任务”。 Which you will have to access by Task.Result.您必须通过 Task.Result 访问它。 This is what you will have to use.这是您必须使用的。

Edit: As @fahadash stated, "wait()" should not be used.编辑:如@fahadash 所述,不应使用“wait()”。 Use "await" instead.请改用“等待”。

Creating a continuation Task that has a result of different type than the first task, with ContinueWith , is not trivial.使用ContinueWith创建一个结果类型不同于第一个任务的延续Task并不简单。 You have to use the Unwrap method in order to flatten the resulting Task<Task<MySecondResult>> , handle carefully the failure and cancellation cases, and specify explicitly the TaskScheduler that will execute the continuation:您必须使用Unwrap方法来展平生成的Task<Task<MySecondResult>> ,小心处理失败和取消情况,并明确指定将执行延续的TaskScheduler

Task<MySecondResult> task = GetFirstResultAsync().ContinueWith(t =>
{
    if (t.IsFaulted)
    {
        var tcs = new TaskCompletionSource<MySecondResult>();
        tcs.SetException(t.Exception.InnerExceptions);
        return tcs.Task;
    }
    if (t.IsCanceled)
    {
        TaskCompletionSource<MySecondResult> tcs = new();
        tcs.SetCanceled(new TaskCanceledException(t).CancellationToken);
        return tcs.Task;
    }
    return GetSecondResultAsync(t.Result);
}, TaskScheduler.Default).Unwrap();

This is quite cumbersome.这是相当麻烦的。 You don't want to have code like this appear frequently in your application code.您不希望在您的应用程序代码中频繁出现这样的代码。 You can either encapsulate this functionality in an extension method, like the Then / ContinueWithResult extension method requested in this GitHub proposal, or use async/await instead of the ContinueWith .您可以将此功能封装在扩展方法中,例如 GitHub 提案中请求的Then / ContinueWithResult扩展方法,或者使用async/await而不是ContinueWith Async/await is composable, so you can write a third async method that combines the GetFirstResultAsync and the GetSecondResultAsync to one: Async/await 是可组合的,因此您可以编写第三个async方法,将GetFirstResultAsyncGetSecondResultAsync为一个:

async Task<MySecondResult> GetSecondAfterFirstAsync()
{
    MyFirstResult result = await GetFirstResultAsync();
    return await GetSecondResultAsync(result);
}

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

相关问题 ComboBox占据2列,在Thread.Task中使用2nd来显示1st - ComboBox taking 2 columns, displaying 1st using 2nd with Thread.Task 如何比较第二个结果和第一个结果 - How to compare 2nd result to 1st result C#线程化,第一个任务DoSomething,第二个任务更新WinFormLabel(实时)? - C# Threading, 1st Task DoSomething, 2nd Task update a WinFormLabel (Realtime)? 使用Regex进行密码强度检查-如何通过第一个验证,但不通过包含示例中的第二个验证? - Password strength checking with Regex - How to pass 1st validation but not the 2nd in included example? Task.ContinueWith不会调用第二个任务(仅第一个正在运行) - Task.ContinueWith does not call 2nd task (only first one is running) 如何在使用任务时使用上一个任务的结果继续使用另一个函数? - How to ContinueWith another function with result from previous task when using Tasks? 如何将异常从ContinueWith传播到无限循环任务的调用上下文 - How to propagate an exception from ContinueWith to the calling context of an infinite loop task WPF-从第一个窗口控制第二个窗口 - WPF - Control 2nd window from 1st window 每当第二个实例的属性更新时,如何更新类的第一个实例的属性? - How to update property of 1st instance of class whenever 2nd instance's property get updated? 如何通过Task.ContinueWith创建传递? - How to create pass through Task.ContinueWith?
 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM