1. 程式人生 > >Event Loop、 巨集任務和微任務

Event Loop、 巨集任務和微任務

本文將介紹我自己對JS `Event Loop` 和 `巨集任務、微任務`的理解。 二話不說先上圖: ![](https://upload-images.jianshu.io/upload_images/7515749-2e1fcbed128544cb.png?imageMogr2/auto-orient/strip%7CimageView2/2/w/1240) 接下來將會針對此圖講解什麼是Event Loop 什麼事巨集任務和微任務(其實聰明的你們通過圖大體也能瞭解的是吧~),再此之前先簡單介紹幾個概念。 ### 為何js是單執行緒 JavaScript的單執行緒,與它的用途有關。作為瀏覽器指令碼語言,JavaScript的主要用途是與使用者互動,以及操作DOM。這決定了它只能是單執行緒,否則會帶來很複雜的同步問題。比如,假定JavaScript同時有兩個執行緒,一個執行緒在某個DOM節點上新增內容,另一個執行緒刪除了這個節點,這時瀏覽器應該以哪個執行緒為準? 所以,為了避免複雜性,從一誕生,JavaScript就是單執行緒,這已經成了這門語言的核心特徵,將來也不會改變。 為了利用多核CPU的計算能力,HTML5提出 Web Worker 標準,允許JavaScript指令碼建立多個執行緒,但是子執行緒完全受主執行緒控制,且不得操作DOM。所以,這個新標準並沒有改變JavaScript單執行緒的本質。(此段來自阮老師) ### 概念 * **同步任務**:在主執行緒上排隊執行的任務,只有前一個任務執行完畢,才能執行後一個任務。 * **非同步任務**:不進入主執行緒、而進入`任務佇列`(Task Queue)的任務。 * **任務佇列**:是一個事件的佇列(也可以理解成訊息的佇列),IO裝置完成一項任務,就在"任務佇列"中新增一個事件,表示相關的非同步任務可以進入"執行棧"了。主執行緒讀取"任務佇列",就是讀取裡面有哪些事件。 ### 詳解圖示 1. 當一段程式碼在主執行緒執行時,會有同步任務和非同步任務,非同步任務會判斷是微任務還是巨集任務,進行不同處理。然後繼續執行當前主執行緒內的程式碼,直到結束。**此段主執行緒執行的的為巨集任務**。 2. 接著上面的判斷,巨集任務的非同步操作會先進入`Event Table`執行,然後當執行結束會把回撥函式推入到`Event Queue` ,然後等待主執行緒的結束。對於微任務的非同步會推入到另外一個`Event Queue` ,等待主執行緒的結束。 3. 當主執行緒結束後,先執行所有的微任務,然後執行把巨集任務的任務佇列(`Event Queue`)中的event拉到主執行緒執行。 4. 一直迴圈前面的操作。至此你應該懂的`EventLoop`了。 備註:如果在執行 microtask(微任務) 的過程中,又產生了microtask,那麼會加入到佇列的末尾,也會在這個週期被呼叫執行。 ### 舉個例子