JS異步宏隊(duì)列與微隊(duì)列原理區(qū)別詳解
1. 原理圖
2. 說(shuō)明
JS 中用來(lái)存儲(chǔ)待執(zhí)行回調(diào)函數(shù)的隊(duì)列包含 2 個(gè)不同特定的列隊(duì)
宏列隊(duì):用來(lái)保存待執(zhí)行的宏任務(wù)(回調(diào)),比如:定時(shí)器回調(diào)、DOM 事件回調(diào)、ajax 回調(diào) 微列隊(duì):用來(lái)保存待執(zhí)行的微任務(wù)(回調(diào)),比如:promise的回調(diào)、MutationObserver 的回調(diào)JS 執(zhí)行時(shí)會(huì)區(qū)別這 2 個(gè)隊(duì)列
JS 引擎首先必須先執(zhí)行所有的初始化同步任務(wù)代碼 每次準(zhǔn)備取出第一個(gè)宏任務(wù)執(zhí)行前, 都要將所有的微任務(wù)一個(gè)一個(gè)取出來(lái)執(zhí)行,也就是優(yōu)先級(jí)比宏任務(wù)高,且與微任務(wù)所處的代碼位置無(wú)關(guān)下面這個(gè)例子可以看出Promise要先于setTimeout執(zhí)行:
setTimeout(() => { //立即放入宏隊(duì)列 console.log(’timeout callback1()’) Promise.resolve(3).then( value => { //立即放入微隊(duì)列 console.log(’Promise onResolved3()’, value) } ) }, 0) setTimeout(() => { //立即放入宏隊(duì)列 console.log(’timeout callback2()’) }, 0) Promise.resolve(1).then( value => { //立即放入微隊(duì)列 console.log(’Promise onResolved1()’, value) setTimeout(() => { console.log(’timeout callback3()’, value) }, 0) } ) Promise.resolve(2).then( value => { //立即放入微隊(duì)列 console.log(’Promise onResolved2()’, value) } ) // Promise onResolved1() 1 // Promise onResolved2() 2 // timeout callback1() // Promise onResolved3() 3 // timeout callback2() // timeout callback3() 1
3. 相關(guān)題目
代碼一:
// 3 7 4 1 2 5 /* 宏: [] 微: [] */ const first = () => (new Promise((resolve, reject) => { console.log(3) let p = new Promise((resolve, reject) => { console.log(7) setTimeout(() => { console.log(5) resolve(6) //會(huì)被忽略,因?yàn)闀?huì)先執(zhí)行微隊(duì)列里的resolve(1),此時(shí)狀態(tài)已經(jīng)改變過(guò)了,且狀態(tài)只能改變一次 }, 0) resolve(1) }) resolve(2) p.then((arg) => { console.log(arg) }) })) first().then((arg) => { console.log(arg) }) console.log(4)
代碼二:
// 1 7 2 3 8 4 6 5 0 setTimeout(() => { console.log('0') }, 0) new Promise((resolve, reject) => { console.log('1') resolve() }).then(() => { console.log('2') new Promise((resolve, reject) => { console.log('3') resolve() }).then(() => { console.log('4') }).then(() => { console.log('5') }) }).then(() => { console.log('6') }) new Promise((resolve, reject) => { console.log('7') resolve() }).then(() => { console.log('8') })
以上就是本文的全部?jī)?nèi)容,希望對(duì)大家的學(xué)習(xí)有所幫助,也希望大家多多支持好吧啦網(wǎng)。
相關(guān)文章:
1. vue實(shí)現(xiàn)web在線聊天功能2. JavaEE SpringMyBatis是什么? 它和Hibernate的區(qū)別及如何配置MyBatis3. JavaScript實(shí)現(xiàn)頁(yè)面動(dòng)態(tài)驗(yàn)證碼的實(shí)現(xiàn)示例4. Springboot 全局日期格式化處理的實(shí)現(xiàn)5. Java使用Tesseract-Ocr識(shí)別數(shù)字6. 完美解決vue 中多個(gè)echarts圖表自適應(yīng)的問(wèn)題7. Python使用urlretrieve實(shí)現(xiàn)直接遠(yuǎn)程下載圖片的示例代碼8. SpringBoot+TestNG單元測(cè)試的實(shí)現(xiàn)9. 在Chrome DevTools中調(diào)試JavaScript的實(shí)現(xiàn)10. 解決Android Studio 格式化 Format代碼快捷鍵問(wèn)題
