前段時間一道筆試題,有點迷糊。今天徹底分析下JS的事件執行機制。【相關推薦:】
各位小夥伴可以試著寫出列印順序
JS
主要作為瀏覽器的指令碼語言,Js
的主要用途是操作DOM,這就決定了JS
必須是單執行緒,如果JS
如Java一樣是多執行緒,如果兩個執行緒同時操作DOM,那麼瀏覽器應該怎麼執行呢?
JS
的釋出其實是為了蹭Java的熱度,其中編寫這門語言的時間並不久,所以這也就是為什麼JS是單執行緒的原因
JS既然是單執行緒,那麼必然會對任務進行一個排序。所有的任務都將按照一個規則執行下去。
同步任務
非同步任務
同步任務和非同步任務進入執行棧中,JS會先判斷任務的型別
是同步任務,直接進入主執行緒
是非同步任務,進入Event Table
中,註冊回撥函數Event Queue
同步任務全部執行結束,JS會Event Queue
中讀取函數執行
這個過程會反覆執行,直到全部任務執行結束。這就是我們常說的事件迴圈
emmmm,我不知道。。。。JS應該有一套自己獨有的邏輯去判斷執行棧是否為空。
非同步的任務執行順序為:宏任務——>微任務
非同步任務可分為
宏任務
微任務
I/0
setTimeout
setInterval
Promise
.then
.catch
vite 之前設定的一個外掛,版本有些問題,不要管這個紅色報警
開始了
是一個同步任務,最先進入執行棧中
執行task()
函數, a
是一個同步任務,進入執行棧中
async/await 是非同步轉同步的過程,第一行程式碼會同步執行,以下的程式碼會非同步。b
作為一個同步任務進入執行棧中
a end
成為了非同步任務的微任務,進入執行棧中,
目前為止,同步任務佇列依次是 開始了
, a
, b
目前為止,非同步任務佇列依次是 宏任務: setTimeout
微任務:a end
那麼問題來了,不是說宏任務會比微任務提前執行嗎,為什麼setTimeout
列印在a end
之後呢?
看這張圖
setTimeout 作為了宏任務進入了任務佇列。所以造成了這種原因
通俗來講:
async await 導致了微任務的產生,但是這個微任務所屬於當前的宏任務。所以會先執行a end
,執行完畢判斷當前宏任務結束。執行下一個宏任務,列印出了setTimeout
c
由於Promise的轉化,變為同步任務進入到任務佇列中
c end
作為Promise衍生的微任務進入任務佇列
d
作為同步任務進入任務佇列
a
b
c
d
a end 微任務
c end 微任務
setTimeout 宏任務
所以列印順序如下
自己對JS執行機制的理解,可能會有些不正確的地方,希望各位大佬指出。
【相關視訊教學推薦:】
以上就是深入分析下JS中的事件執行機制的詳細內容,更多請關注TW511.COM其它相關文章!