settimeout,promise,async执行顺序

mac2026-05-21  11

async function async1() { console.log("async1 start"); await async2(); console.log("async1 end"); } async function async2() { console.log( 'async2'); } console.log("script start"); setTimeout(function () { console.log("settimeout"); },0); async1(); new Promise(function (resolve) { console.log("promise1"); resolve(); }).then(function () { console.log("promise2"); }); console.log('script end');

代码运行结果为 接下来我们一行行解释: 开始申明了async1和async2两个异步函数,在async中调用了async这个函数,但是只是申明,并没了直接调用。 所以一开始输出 script start

接下来运行到了settimeout,settimeout是一个异步宏任务,事件循环是一个宏任务-微任务的循环,整个script算是一次宏任务,所以遇到了settimeout只是将settimeout放到了宏任务的任务队列中,暂时不去处理它。

接下来调用了async1函数,一开始输出了async1 start,然后在调用了async2函数,await是一个让出线程的标志,先去执行async2函数,输出了async2,接着会跳出整个async函数执行后面的js代码,等本轮任务循环结束后再执行await后面的代码。

接下来到了promise,promise是一个对象,它的构造函数里面还是同步执行的,所以输出promise1,然后因为promise是一个异步微任务,会将返回的结果也就是then或者是catch的回调加入异步微任务的任务队列中。

接着输出script end,代表本次的宏任务执行完成了。记得上面提到的await,在本次宏任务执行完成后执行,输出async1 end。

接下来,js引擎会找微任务队列,如果有微任务存在则执行读取微任务,上面说到了,promise.then里面是异步微任务的操作,所以输出promise2。

到此,一次宏任务和一次微任务已经执行结束。

接下来js引擎接着会找宏任务队列中的任务,读取settimeout这个任务,输出settimeout。

参考文献: js浏览器事件循环

最新回复(0)