本文受https://segmentfault.com/a/1190000015057278文章啓發。
不過感覺作者寫得比較冗餘,且有些東西還是沒有講明白。於是我嘗試用更進階的代碼並配上更簡潔的註釋來講明白這些事情。
1. 事件循環
js在執行的過程中是單線程的,所以採用了事件循環機制。也就是說,從上往下執行。執行完畢 => 判斷是否
微任務
=> 判斷是否有宏任務
2.回調隊列
宏任務目前就簡單的理解爲setTimeout就ok了。而微任務就理解爲回調函數的回調隊列,這裏包含await promise callback。
某種意義上來說, await 是 對 promise 的封裝 , 而 promise 又是對 callback 的封裝。所以,其實是一回事兒。
即使看不懂上邊的兩點也無所謂,下面進入重點,廢話少說,直接貼代碼。
async function async1(){
console.log('async1 start')
console.log('async1 print',await async2())
console.log('async1 end')
}
async function async2(){
console.log('async2 start')
console.log('async2 print',await async3())
console.log('async2 end')
}
async function async3(){
console.log('async3')
}
console.log('進程 start')
setTimeout(function(){
console.log('setTimeout1')
},0)
setTimeout(function(){
console.log('setTimeout2')
},0)
async1();
new Promise(function(resolve){
console.log('promise1')
resolve();
}).then(function(){
console.log('promise1 resolve')
})
new Promise(function(resolve){
console.log('promise2')
resolve();
}).then(function(){
console.log('promise2 resolve')
})
console.log('進程 end')
看起來其實挺繞的,如果你看了開篇那篇文章,且看不明白,那你就看我的吧。雖然更復雜,但我覺得我講得更清楚一些。
---------- 主進程開始
1. 進程start
2. 執行函數 async1, 打印 async1 start, 碰到await async2.
3. 執行函數 async2, 打印 async2 start, 碰到await async3.
4. 執行函數 async3, 打印 async3, 並返回回調隊列1,函數繼續往下執行.
5. 執行Promise , 打印promise1, 並返回回調隊列2, 函數繼續往下執行.
6. 執行Promise , 打印promise2, 並返回回調隊列3, 函數繼續往下執行。
7. 進程end
--------- 主進程結束
--- 微任務開始
---------- 回調隊列
8. 處理回調隊列1, 執行完async3, 返回給 async2, 打印 async2 print undefined, async2 end, 返回回調隊列1
9. 處理回調隊列2, 打印 promise1 resolve
10. 處理回調隊列3, 打印 promise2 resolve
---------- 第二次回調隊列
11. 處理時間隊列1, 執行完async2, 返回給 async1, 打印 async1 print undefined, async1 end, 此時回調隊列爲空
--- 微任務結束
--- 宏任務開始
---------- 執行事件循環
12. setTimeout1
13. setTimeout2
--- 宏任務結束
全部結束
也就是說最後執行的結果爲:
進程 start
async1 start
async2 start
async3
promise1
promise2
進程 end
async2 print undefined
async2 end
promise1 resolve
promise2 resolve
async1 print undefined
async1 end
setTimeout1
setTimeout2
有不明白的歡迎留言。