博客
关于我
强烈建议你试试无所不能的chatGPT,快点击我
一文彻底搞懂Dart的event队列
阅读量:6279 次
发布时间:2019-06-22

本文共 3654 字,大约阅读时间需要 12 分钟。

概念介绍

event队列和microtask是dart包里的代码,这部分知识是做Flutter必懂的知识,至于event队列和microtask是什么自己谷歌,我就不赘述了。然后我发一段代码,在不运行的情况下,请思考输出什么

第一次练习

void main() {  methodA();  methodB();  methodC('main');  methodD();}methodA(){  print('A');}methodB() async {  print('B start');  await methodC('B');  print('B end');}methodC(String from) async {  print('C start from $from');  Future((){    print('C running Future from $from');  }).then((_){    print('C end of Future from $from');  });  print('C end from $from');}methodD(){  print('D');}复制代码

我们可以分析一下,main是同步方法,所以在main方法里调用的方法如果是async的,会执行到await然后返回future,先看methodA();这个不用多说直接输出A。然后看methodB();,因为main是同步方法所以在await之前的直接运行,所以输出B start,然后运行到await methodC('B');,会把methodB加入到event事件队列,然后进入methodC方法直到运行到await方法之前,所以输出C start from BC end from BFuture方法里的内容不输出是因为在这里只是把这个Future加入到event事件队列,然后运行到methodC('main'),同刚才一样,输出C start from mainC end from main,这里的Future方法也是加到了event事件队列,然后执行methodD()方法,输出D,然后同步方法main执行完毕,开始执行event事件队列里的事件,按照刚才加入event事件队列的顺序,先执行methodB(),打印B end,然后打印C running Future from BC end of Future from BC running Future from mainC end of Future from main

添加注释后的代码如下

void main() {  methodA();  methodB();  methodC('main');  methodD();}methodA(){  print('A');//1}methodB() async {  print('B start');//2  await methodC('B');//2之后加入到了event队列  print('B end');//8}methodC(String from) async {  print('C start from $from');//3、5  Future((){//3之后加到了event队列,from=B、5之后加到了event队列,from=main    print('C running Future from $from');  }).then((_){    print('C end of Future from $from');  });  print('C end from $from');//4、6}methodD(){  print('D');//7}复制代码

打印结果如下所示:

AB startC start from BC end from BC start from mainC end from mainDB endC running Future from BC end of Future from BC running Future from mainC end of Future from main复制代码

第二次练习

然后我们换一种方式,代码如下

void main() async {  methodA();  await methodB();  await methodC('main');  methodD();}methodA(){  print('A');}methodB() async {  print('B start');  await methodC('B');  print('B end');}methodC(String from) async {  print('C start from $from');  Future((){    print('C running Future from $from');  }).then((_){    print('C end of Future from $from');  });  print('C end from $from');}methodD(){  print('D');}复制代码

开始我们的分析,这次的main方法改成了async的,首先输出A,然后执行到await methodB(),进入methodB()方法,输出B start,然后执行await methodC('B'),然后输出C start from B,然后Future加入事件队列,然后输出C end from B,然后这次和上次开始有区别了,因为这次的main方法是async的方法,所以在await methodB()这里会等待methodB()方法执行完毕,所以下一步输出B end,然后执行methodC('main'),输出C start from main,然后Future加入事件队列,然后输出C end from main,然后执行methodD()输出D,然后开始从event队列取事件,按照刚才加入event队列的顺序,一次输出C running Future from BC end of Future from BC running Future from mainC end of Future from main

添加注释后的代码如下

void main() async {  methodA();  await methodB();  await methodC('main');  methodD();}methodA(){  print('A');//1}methodB() async {  print('B start');//2  await methodC('B');//因为main方法是async的,所以这里没有加入到event队列而是继续执行  print('B end');//5}methodC(String from) async {  print('C start from $from');//3 6  Future((){//3之后加入到event队列、6之后加入到event队列    print('C running Future from $from');  }).then((_){    print('C end of Future from $from');  });  print('C end from $from');//4 7}methodD(){  print('D');//8}复制代码

打印结果如下所示

AB startC start from BC end from BB endC start from mainC end from mainDC running Future from BC end of Future from BC running Future from mainC end of Future from main复制代码

总结

如果async的方法被同步方法调用,代码会执行到第一个await之前,然后把当前future加入到event队列;如果async的方法被async的方法调用,那么在执行到await的时候会等待执行完毕。

还有一个microtask,原理和这个一样,混合使用的时候,在主方法执行完毕以后,会先取microtask队列的事件执行,都执行完以后再从event队列里取事件执行。

有问题请留言,欢迎加入QQ群:,如果你是一个喜欢思考的人,欢迎加入群一起交流学习,拒绝伸手党。

转载于:https://juejin.im/post/5d031adb6fb9a07efd47092d

你可能感兴趣的文章
embedded linux学习中几个需要明确的概念
查看>>
mysql常用语法
查看>>
Morris ajax
查看>>
【Docker学习笔记(四)】通过Nginx镜像快速搭建静态网站
查看>>
ORA-12514: TNS: 监听程序当前无法识别连接描述符中请求的服务
查看>>
<转>云主机配置OpenStack使用spice的方法
查看>>
java jvm GC 各个区内存参数设置
查看>>
[使用帮助] PHPCMS V9内容模块PC标签调用说明
查看>>
关于FreeBSD的CVSROOT的配置
查看>>
基于RBAC权限管理
查看>>
基于Internet的软件工程策略
查看>>
数学公式的英语读法
查看>>
留德十年
查看>>
迷人的卡耐基说话术
查看>>
PHP导出table为xls出现乱码解决方法
查看>>
PHP问题 —— 丢失SESSION
查看>>
PyCairo指南--目录
查看>>
Java中Object类的equals()和hashCode()方法深入解析
查看>>
Linux/centos 下挂载硬盘的 方法
查看>>
数据库
查看>>