Promise在前端中主要用于处理异步调用,其基本使用方式通过阮一峰大佬的文档一下就可以入手,但是最近我看了一篇文章wecTeam中,作者深山蚂蚁的《高级进阶:深度揭秘Promise注册微任务和执行过程》一文,让我对Promise的执行顺序有了更深的了解,与此同时我也有了一个疑问,通过这篇文章与大家探讨。
1. promise的异步主要发生在微任务队列中
2. 第一个then的回调监听最新Promise对象的resolve执行后才会注册进微任务队列,之后的then回调都依赖于前一个then中的代码执行结束。
下面的内容主要基于两个概念讨论:
(1) 当前一个then中的代码都是同步执行的,执行结束后第二个then即可注册进入微任务队列。
(2) 当前一个then中有return 关键字,需要return的内容完全执行结束,第二个then才会注册进入微任务队列。
then也分下面几种情况:
// Case 1: 前一个then中的代码都是同步的
new Promise( (resolve) => { resolve();})
.then(() => {console.log(1);})
.then(() => {console.log(2)});
// 输出
// 1
// 2
// Case 2: 前一个then中的代码 return一个Promise对象
new Promise((r,rj) => {
console.log('外p');
r();
}).then(() => {
console.log('外then1');
new Promise(((r,rj) => {
console.log('内p');
r();
})).then(() => {
console.log('内then1');
return new Promise((r, rj) => {r();});
}).then(() => {
console.log('内then2');
});
}).then(() => {
console.log('外then2');
}).then(() => {
console.log('外then3');
}).then(() => {
console.log('外then4');
});
/**
输出结果:
"外p"
"外then1"
"内p"
"内then1"
"外then2"
"外then3"
"外then4"
"内then2"
**/
我自己疑惑的主要是Case2这种情况,为什么"内then2"会在"外then4"之后打印?
return new Promise((r, rj) => {r();}) 等同于
return new Promise((r, rj) => {r();}).then(()=>{console.log(1)}).then(()=>{console.log(2)}).then(()=>{console.log(3)});
这里面究竟藏着什么原因?