当你等待一个失败的任务,会发生什么 [英] What happens when you await a failed task
问题描述
我给你一个理论问题。如果我在等待着另一个任务内的任务的结果会发生什么?我想知道如果我当前系统将事后工作。
一个任务被推出,并做一些事情。在某些时候该任务可能需要为了处理该当前任务是不能够通过自身来处理数据另一个。所以,我用等待来确保目前的任务不会,只要他还没有辅助任务的结果继续进行。但是,如果辅助失败会发生什么? ?将当前的任务保持锁定
我能避免这种僵局在某种程度上(在不改变系统本身 - 内任务的任务)
一个任务被推出,并做一些事情。在某些时候该任务可能需要为了处理该当前任务是不能够通过自身来处理数据另一个。所以,我用等待来确保目前的任务不会,只要他还没有辅助任务的结果继续进行。但是,如果辅助失败会发生什么?将当前的任务仍然锁定?
块引用>
背后
的核心思想异步
和等待
是异步代码的工作几乎一样同步码。
所以,如果你有这样的同步码
无效HelperMethod()
{
抛出新的InvalidOperationException异常(测试);
}
无效DoStuff()
{
HelperMethod();
}
那么,你会期望
DoStuff
从辅助方法,传播出现InvalidOperationException
。同样,与异步代码会发生什么:异步任务HelperMethodAsync()
{
抛出新的InvalidOperationException异常(测试);
}
异步任务DoStuffAsync()
{
等待HelperMethodAsync();
}
这就是
DoStuffAsync
也将传播出现InvalidOperationException
。
现在,这是行不通的究竟的以同样的方式,当然,因为它必须是异步的,但总的想法是,所有的控制流,如
尝试
/抓
,为
循环,等等,所有的只是工作为异步代码非常相似同步码。
什么是的实际的事情是,当
HelperMethod
与出现InvalidOperationException
,异常结束被捕获并放置在返回工作
,并且任务完成。当等待
在DoStuffAsync
看到该任务已经完成,它将检查异常,并重新提出第一个(在这种情况下,仅存在一个,在InvalidOperationException异常
)。并重新加注它,保留异常调用堆栈上的方法。这反过来会导致工作
从DoStuffAsync
来与相同的异常完成返回。
所以,在被窝里
异步
和等待
正在做一些工作,以确保你可以叫用其他方法等待
,并使用尝试
/抓
的方式,你会在同步码相同。但大多数时候,你不必意识到这一点。I have a theoretical question to you. What happens if I await the Result of a Task inside another task? I want to know if my current system will work afterwards.
A task gets launched and does some stuff. At some point that task might need another one in order to process data which the current task is not able to process by itself. So I use await to ensure that the current task won't continue as long as he has not the result of the helper task. But what happens if the helper fails? Will the current task remain locked?
Can I avoid this deadlock somehow (without changing the system itself - task inside task)?
解决方案A task gets launched and does some stuff. At some point that task might need another one in order to process data which the current task is not able to process by itself. So I use await to ensure that the current task won't continue as long as he has not the result of the helper task. But what happens if the helper fails? Will the current task remain locked?
The core idea behind
async
andawait
is that asynchronous code works just about the same as synchronous code.So, if you have synchronous code like this:
void HelperMethod() { throw new InvalidOperationException("test"); } void DoStuff() { HelperMethod(); }
then you would expect
DoStuff
to propagate theInvalidOperationException
from the helper method. Similarly, that's what happens with asynchronous code:async Task HelperMethodAsync() { throw new InvalidOperationException("test"); } async Task DoStuffAsync() { await HelperMethodAsync(); }
That is,
DoStuffAsync
will also propagate theInvalidOperationException
.Now, it doesn't work exactly the same way, of course, since it must be asynchronous, but the general idea is that all your control flow such as
try
/catch
,for
loops, etc, all "just work" for asynchronous code very similarly to synchronous code.What's actually going on is that when
HelperMethod
ends with anInvalidOperationException
, the exception is caught and placed on the returnedTask
, and the task is completed. When theawait
inDoStuffAsync
sees that the task has completed, it examines its exceptions and re-raises the first one (in this case, there is only one, theInvalidOperationException
). And it re-raises it in a way that preserves the call stack on the exception. This in turn causes theTask
returned fromDoStuffAsync
to be completed with that same exception.So, under the covers
async
andawait
are doing a bit of work to ensure that you can just call other methods withawait
and usetry
/catch
the same way as you would in synchronous code. But most of the time you don't have to be aware of that.这篇关于当你等待一个失败的任务,会发生什么的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!