并发系列64章(异步编程三)第四章
前言
续写第三章,结束掉一些例子。
避免上下文延续
这是什么意思呢?
是这样的,在默认情况下,一个async 方法在被await调用恢复的时候呢,会在原来的上下文中运行。
啥上下文?那么什么是上下文呢?在我们以前做语文的时候,请参考上下文然后怎么怎么的。
这个上下文,其实就是状态。比如说我看一篇文章,看到了第三句,说的是"他轻轻的走了"。那么这个他是谁?
那么我们结合第一句,"远远的他来了,往近一瞅,他是小明。" 那么他就是小明。前面的上下文就是状态。
每一个async都是一篇文章,都有上下文状态,当切换await的时候,还有继续往下看,那么就要切换上下文。
那么async 这个状态是啥?
从使用async修饰符修饰的方法的IL代码可以得出一个结论:
在Debug下,针对async方法,生成的是一个class状态机
在Release下,针对async方法,生成的是一个struct状态机
这个上下文就是状态机。
那么这个状态机是啥?为了避免我写第五章还是异步编程,在此只做简单介绍。
1.每个async 都有一个状态机,状态机控制着async方法的运行。
2.状态机的状态为:-1:初始化;-2:方法体执行结束;1:第一个await;2:第二个await是否完成。
具体这个状态机丢弃了,有什么副作用呢?
请用ILSpy 反编译查看,涉及到原理。
我在后续中,我会写一章反编译来解释await 和 async 的原理,仅仅是个人理解。
处理async void 方法的异常
首先说一下为什么不推荐使用async 返回void呢?
这就有一个问题,如果我们做地铁的时候,总部不知道地铁跑到哪里了,这是否是一个问题?因为不返回task,那么到底啥情况呢?
但是void 有必须存在,例如命令式的异步事件,因为没有返回task意义何在。
什么是命令式的?
比如说winfrom的异步事件,我点击了一个按钮。
这种就是命令式的。我只是触发了点击按钮这个事件,这个事件调用我们的程序。至于点击之后发生什么,没有必要知道。
那么如何测试async void 呢?
这里面介绍了,我就不啰嗦了。
结尾
下一章 并行编程。