.net 如何更改任务中的值

gfttwv5a  于 2023-02-20  发布在  .NET
关注(0)|答案(2)|浏览(131)

我有一个async函数。有多个级别的函数调用都返回一个Task。在这个链中的某个点上,我必须修改结果的值。我希望在不中断async函数流的情况下完成此操作。请注意:

[HttpGet]
[Route("GetWeb")]
public async Task<IHttpActionResult> GetResult([FromUri] string url)
{
    var result = await GetPageText(url);
    return Ok(result);
}

private Task<string> GetPageText(string url)
{
    Task<string> data = GetDataAsync(url);
    //here I would like to manipulate the data variable
    return data;
}

在函数GetPageText中,我如何在不中断异步流的情况下操作数据变量,这可能吗?

fkaflof6

fkaflof61#

你不能改变一个任务的值,你需要创建一个新的,async的方法是等待原始的结果,并将方法标记为async(只有当你需要原始任务的结果时才会这样):

private async Task<string> GetPageText(string url)
{
    var result = await GetDataAsync(url);
    return result + "bar";
}
yzxexxkh

yzxexxkh2#

你也可以用ContinueWith来表达,这样就避免了await,所以你的代码不必停下来等待,我相信这样更安全,更高效。

private Task<string> GetPageText(string url)
{
    Task<string> data = GetDataAsync(url);
    data.ContinueWith(t => t.Result + "Bar")

    return data;
}

这样,代码就不会等待。它只是设置代码,以便在结果可用时继续执行任务并进行进一步处理。这可以在代码返回很久之后发生,而不是在代码中等待。
最好避免在异步任务中等待。
当异步方法直接等待任务时,根据异步上下文的不同,继续通常发生在创建任务的同一线程中。这种行为可能会影响性能,并可能导致UI线程死锁。
analyzers that will flag this
这个问题在九年前可能就已经提出了,但是使用ContinueWith()ConfigureAwait(false)或者避免使用await在现在甚至在过去都是处理这个问题的最好方法,而使用ContinueWith()完美地捕捉到了在调用者看到之前对任务结果进行额外操作的意图。

相关问题