好家伙,本篇为做题思考

书接上文

 

题目如下:

 1.请给出下列代码的输出结果,并配合"消息队列"写出相关解释

async function foo() {
console.log(2);
console.log(await Promise.resolve(8));
console.log(9);
}
async function bar() { console.log(4);
console.log(await 6);
console.log(7);
}
console.log(1);
foo();
console.log(3);
bar();
console.log(5);

 

好我们公布答案:

(1) 打印 1;

(2) 调用异步函数 foo();

(3)(在 foo()中)打印 2;

(4)(在 foo()中)await 关键字暂停执行,向消息队列中添加一个期约在落定之后执行的任务;

(5) 期约立即落定,把给 await 提供值的任务添加到消息队列;

(6) foo()退出;

(7) 打印 3;

(8) 调用异步函数 bar();

(9)(在 bar()中)打印 4;

(10)(在 bar()中)await 关键字暂停执行,为立即可用的值 6 向消息队列中添加一个任务;

(11) bar()退出;

(12) 打印 5;

(13) 顶级线程执行完毕;

(14) JavaScript 运行时从消息队列中取出解决 await 期约的处理程序,并将解决的值 8 提供给它;

(15) JavaScript 运行时向消息队列中添加一个恢复执行 foo()函数的任务;

(16) JavaScript 运行时从消息队列中取出恢复执行 bar()的任务及值 6;

(17)(在 bar()中)恢复执行,await 取得值 6;

(18)(在 bar()中)打印 6;

(19)(在 bar()中)打印 7;

(20) bar()返回;

(21) 异步任务完成,JavaScript 从消息队列中取出恢复执行 foo()的任务及值 8;

(22)(在 foo()中)打印 8;

(23)(在 foo()中)打印 9;

(24) foo()返回。

 

所以答案是

1

2

3

4

5

6

7

8

9

 

好了,结束了,没什么问题了

步骤也解释清楚了

 

但是我隐约感到了不对劲

怎么会是123456789呢?

foo()应该是先恢复的,但是这里明显bar()先恢复了

我们上机试一下

 

 

诶,结果不对

前面地12345都没有问题,6789的输出变成了8967

我们主要来看和6789有关的输出字段

我们再来仔细地看看前面地解释,并把关键解释划出来

(4)(在 foo()中)await 关键字暂停执行,向消息队列中添加一个期约在落定之后执行的任务;

(5) 期约立即落定,把给 await 提供值的任务添加到消息队列;

(6) foo()退出;

(10)(在 bar()中)await 关键字暂停执行,为立即可用的值 6 向消息队列中添加一个任务;

(11) bar()退出;

(13) 顶级线程执行完毕;

(14) JavaScript 运行时从消息队列中取出解决 await 期约的处理程序,并将解决的值 8 提供给它;

(15) JavaScript 运行时向消息队列中添加一个恢复执行 foo()函数的任务;

(16) JavaScript 运行时从消息队列中取出恢复执行 bar()的任务及值 6;

我们回顾一下消息队列

一个 JavaScript 运行时包含了一个待处理消息的消息队列。. 每一个消息都关联着一个用以处理这个消息的回调函数。

再补充一个关于await的知识点

等到 await 右边的值可用了,JavaScript 运行时会向消息 队列中推送一个任务,这个任务会恢复异步函数的执行。

我们试着把这个消息队列画出来

(有点抽象,但应该能看懂)

这样,我们就会发现, 因为Promise.resolve(8)被多处理了一次,导致了foo()方法后恢复

所以bar()先恢复了

那么实际上机又是怎么回事呢?

(书里面有行小字被我忽略了,后面又找到了)

 TC39 对 await 后面是期约的情况如何处理做过一次修改。修改后,本例中的 Promise.resolve(8)只会生成一个 异步任务。

因此在新版浏览器中,这个示例的输出结果为 123458967。实际开发中,对于并行的异步操作我们通常 更关注结果,而不依赖执行顺序。——译者注

实际上机的消息队列

原先的两步处理变成了一步

搞定了,原来如此

第127篇:异步函数(async和await)练习题(异步,消息队列)的更多相关文章

  1. 令人清爽的异步函数async、await

    1.什么是async.await? async用于声明一个函数是异步的.而await从字面意思上是"等待"的意思,就是用于等待异步完成.并且await只能在async函数中使用; ...

  2. vue中异步函数async和await的用法

    整理的不错,收藏一下 http://blog.sina.com.cn/s/blog_13d06fc1f0102wzfr.html

  3. .net 异步函数 Async await

    .net  异步函数  Async await 一旦为函数添加async关键字 该函数就是一个异步函数. 异步方法必须返回 void 或 Task<> 类型. public static ...

  4. 反爬虫:利用ASP.NET MVC的Filter和缓存(入坑出坑) C#中缓存的使用 C#操作redis WPF 控件库——可拖动选项卡的TabControl 【Bootstrap系列】详解Bootstrap-table AutoFac event 和delegate的分别 常见的异步方式async 和 await C# Task用法 c#源码的执行过程

    反爬虫:利用ASP.NET MVC的Filter和缓存(入坑出坑)   背景介绍: 为了平衡社区成员的贡献和索取,一起帮引入了帮帮币.当用户积分(帮帮点)达到一定数额之后,就会“掉落”一定数量的“帮帮 ...

  5. 使用 Async 和 Await 的异步编程(C# 和 Visual Basic)[msdn.microsoft.com]

    看到Microsoft官方一篇关于异步编程的文章,感觉挺好,不敢独享,分享给大家. 原文地址:https://msdn.microsoft.com/zh-cn/library/hh191443.asp ...

  6. 【转】【C#】C# 5.0 新特性——Async和Await使异步编程更简单

    一.引言 在之前的C#基础知识系列文章中只介绍了从C#1.0到C#4.0中主要的特性,然而.NET 4.5 的推出,对于C#又有了新特性的增加--就是C#5.0中async和await两个关键字,这两 ...

  7. 使用Async和Await进行异步编程(C#版 适用于VS2015)

    你可以使用异步编程来避免你的应用程序的性能瓶颈并且加强总体的响应.然而,用传统的技术来写异步应用是复杂的,同时编写,调试和维护都很困难. VS2012介绍了简单的方法,那就是异步编程,它在.Net F ...

  8. 使用Async和Await进行异步编程(C#版 适用于VS2015) z

    你可以使用异步编程来避免你的应用程序的性能瓶颈并且加强总体的响应.然而,用传统的技术来写异步应用是复杂的,同时编写,调试和维护都很困难. VS2012介绍了简单的方法,那就是异步编程,它在.Net F ...

  9. Async和Await进行异步编程

    使用Async和Await进行异步编程(C#版 适用于VS2015) 你可以使用异步编程来避免你的应用程序的性能瓶颈并且加强总体的响应.然而,用传统的技术来写异步应用是复杂的,同时编写,调试和维护都很 ...

  10. 【C#复习总结】 Async 和 Await 的异步编程

    谈到异步,必然要说下阻塞,在知乎上看到了网友举的例子非常省动,在这里我引用下. 怎样理解阻塞非阻塞与同步异步的区别? 老张爱喝茶,废话不说,煮开水. 出场人物:老张,水壶两把(普通水壶,简称水壶:会响 ...

随机推荐

  1. pytest-数据驱动

    今天介绍两种实现数据驱动的方法,json和excel,我们以获取企业微信token接口为例,共 有两个参数corpid&corpsecret 一.json 方法一:@pytest.mark.p ...

  2. TortoiseGit 常见问题汇总

    1.test分支修改后合并到master分支 1)切换本地分支到master分支 2)TortoiseGit --->  merge,选择远程分支test 提交到远程分支master 2.将远程 ...

  3. 每日一库:cobra 简介

    当你需要为你的 Go 项目创建一个强大的命令行工具时,你可能会遇到许多挑战,比如如何定义命令.标志和参数,如何生成详细的帮助文档,如何支持子命令等等.为了解决这些问题,github.com/spf13 ...

  4. C# 求两个时间的差值

    商品保质期 //dateStart:系统时间: dateEnd :物品到期日期 DateTime dateStart = DateTime.Now.Date;//2021/7/8 DateTime d ...

  5. BigDecimal详解和精度问题

    JavaGuide :「Java学习+面试指南」一份涵盖大部分 Java 程序员所需要掌握的核心知识. BigDecimal 是大厂 Java 面试常问的一个知识点. <阿里巴巴 Java 开发 ...

  6. 强化学习从基础到进阶-案例与实践[3]:表格型方法:Sarsa、Qlearning;蒙特卡洛策略、时序差分等以及Qlearning项目实战

    强化学习从基础到进阶-案例与实践[3]:表格型方法:Sarsa.Qlearning:蒙特卡洛策略.时序差分等以及Qlearning项目实战 策略最简单的表示是查找表(look-up table),即表 ...

  7. 解决问题:latex中bib引用顺序不正确,引用顺序和正文不一致

    问题:生成pdf时文献应用会乱序 引用bib格式的参考文献时,会这么写: \bibliographystyle{plain} \bibliography{%filename%.bib} 而plain的 ...

  8. 数据挖掘机器学习[四]---汽车交易价格预测详细版本{嵌入式特征选择(XGBoots,LightGBM),模型调参(贪心、网格、贝叶斯调参)}

    题目出自阿里天池赛题链接:零基础入门数据挖掘 - 二手车交易价格预测-天池大赛-阿里云天池 相关文章: 特征工程详解及实战项目[参考] 数据挖掘---汽车车交易价格预测[一](测评指标:EDA) 数据 ...

  9. 【STL源码剖析】stack_queue底层模拟实现 | 什么是适配器?【超详细的底层注释和解释】

    今天博主继续带来STL源码剖析专栏的第四篇博客了! 今天带来stack和queue的模拟实现!话不多说,直接进入我们今天的内容! 前言 那么这里博主先安利一下一些干货满满的专栏啦! 手撕数据结构htt ...

  10. 【排序】什么都能排的C语言qsort排序详解【超详细的宝藏级别教程】深度理解qsort排序

    [排序]什么都能排的C语言qsort排序详解[超详细的宝藏级别教程]深度理解qsort排序 作者: @小小Programmer 这是我的主页:@小小Programmer 在食用这篇博客之前,博主在这里 ...