繁体   English   中英

异步任务的返回值是多少?

[英]What is the return value of async Task?

想象一下我有这个async方法:

public async Task Foo(object fooObj)
{
    //do foo's stuff.
    //maybe set a fooable static global variable
    //or write some data to fooObj
}

并这样称呼:

public async void FooCaller()
{
    await Foo(new dummyObject)
}

好的,这样:第一个代码块返回Task ,但实际上并没有在任何地方返回。

我可以想象async关键字的情况有一些编译器异常,否则需要返回值。

但是如果是这种情况,返回值如何初始化? (好的,我可以自己检查一下)。

更重要:

使用此模式时有任何陷阱吗? (例如:访问fooObj ,延迟执行时间等。)

好的,这样:第一个代码块返回一个Task,但实际上并没有在任何地方返回。

确实。 您可以将其视为Task<void> -如果有效的话。 它用于指示异步方法何时完成。

基本上,任何非无效异步方法都会包装您在任务中返回的内容。 因此,例如:

async Task<string> FooAsync()
{
    // Do some async operations
    return "foo";
}

请注意, return语句中的表达式类型为string ,但是方法的声明返回类型为Task<string> 编译器会完成所有工作,以将异步操作包装在合适的Task ,该Task在方法完成或引发异常时完成。 (在这种情况下,返回的Task处于“故障”状态。)

之所以需要这样做,是因为对async方法的调用通常在该方法完成之前返回 认为方法调用是“请开始做某事”-它会启动它并返回,但是您想知道“某事”何时完成以及结果是什么。

await表达式执行相反的展开操作 -仅在等待操作完成后才继续通过该方法,并展开该值(例如,使用Task.Result )。 但是与其阻塞,不如使它立即返回。 这就是等待其他异步方法结果的异步方法如何很好地进行合成的方式。

一旦将string挂在Task<string>包装上,并在await任务时进行了等效的拆包,就可以很容易地看到Taskvoid的类比。 因此,这对void方法有效:

void Foo()
{
    // Do some actions.
    ...
    // No need for a return statement
}

async Task方法也是如此:

async Task Foo()
{
    // Do some actions (presumably using await)
    ...
    // No need for a return statement
}

可以async Task方法中使用return语句(无值):

async Task Foo()
{
    if (weDontNeedToDoAnything)
    {
        return; // This is fine
    }
    // Do some actions (presumably using await)
    ...
    // No need for a return statement
}

暂无
暂无

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

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM