首頁 > web前端 > js教程 > 事件循環——JavaScript

事件循環——JavaScript

Mary-Kate Olsen
發布: 2024-12-04 04:13:14
原創
534 人瀏覽過

Event Loop — JavaScript

事件循環是維護 JavaScript 程式碼執行順序(處理非同步操作而不阻塞主執行緒)的循環。

在深入事件循環之前需要了解的事情:

  1. 呼叫堆疊:這是 JavaScript 執行程式碼的地方。它遵循後進先出 (LIFO) 結構。當呼叫函數時,會建立一個新的執行上下文並將其推入堆疊。當功能結束時,它會彈出。
  2. MicroTasks 隊列:專用於queueMicroTask 方法、Promise 處理程序、特殊隊列回呼和MutationObserver(介面提供了監視 DOM 樹所做變更的能力)。 MacroTasks 隊列:來自Web API 的所有其他回調(
  3. setTimeoutsetIntervalDOM API , fetch)進入巨集任務佇列。
  4. 什麼是事件循環?

這是一個無限循環,等待任務並將其推送到呼叫堆疊中執行。由於 JavaScript 是單執行緒的,它會維護一個執行順序來根據優先權處理同步非同步操作。

    常規 JS 程式碼:
  1. 同步程式碼首先運行並填入呼叫堆疊。
  2. MicroTasks:
  3. 在 microTasks 佇列中排隊的任務被執行。
  4. MacroTasks:
  5. 在 MacroTasks 佇列中排隊的任務被執行。
讓我們透過一個範例來更好地理解工作流程
// Programmatic way of how the event loop processes tasks
while (true) {
  // Step 1: Execute tasks in the call stack
  while (!callStack.isEmpty()) {
    const currentTask = callStack.pop();
    currentTask(); // Executes the task
  }
  // Step 2: Process all microtasks
  while (!microTasksQueue.isEmpty()) {
    const microTask = microTasksQueue.shift();
    callStack.push(microTask); // Push microtask to call stack for execution
  }
  // Step 3: Process one macrotask if available
  if (!macroTasksQueue.isEmpty()) {
    const macroTask = macroTasksQueue.shift();
    callStack.push(macroTask); // Push macrotask to call stack for execution
  }
  // Break if there's nothing left to process
  if (callStack.isEmpty() && microTasksQueue.isEmpty() && macroTasksQueue.isEmpty()) {
    break;
  }
}
登入後複製


假設我們有 2 個隊列
1.  setTimeout(() => console.log(1), 2000);
2.  Promise.resolve().then(() => {
3.      console.log(2);
4.      queueMicroTask(() => console.log(3));
5.  });
6.  Promise.resolve().then(() => {
7.      console.log(4);
8.      setTimeout(() => console.log(5));
9.  });
10. setTimeout(() => console.log(6));
11. console.log(7);

// 7 2 4 3 6 5 1
登入後複製

microTasksmacroTasks。當程式碼開始執行時,

  1. ()=> console.log(1) 在 2000 毫秒內被推入 macroTasks 佇列。
  2. ()=> { 控制台.log(2); queueMicroTask(() => console.log(3)); }) 被推入 microTasks 佇列。
  3. ()=> { 控制台.log(4); setTimeout(() => console.log(5)); }) 被推入 microTasks 佇列。
  4. ()=> console.log(6) 在 0 毫秒內被推入 macroTasks 佇列。
  5. console.log(7) 執行並在控制台中列印 7。
  6. 現在事件循環檢查microTasks 佇列中的任務並採取() =>; { 控制台.log(2); queueMicroTask(() => console.log( 3)); }) 任務並在控制台中列印2 並推送() =>; console.log(3) 進入microTasks 隊列。
  7. 接下來,事件循環檢查microTasks 隊列並採取() =>; { 控制台.log(4); setTimeout(() => console.log(5 )); }) 任務並列印4 並推送() => console.log(5) 在0 毫秒內寫入macroTasks 隊列。
  8. 事件循環再次檢查microTasks佇列並採取() =>; console.log(3)) 任務並在控制台中列印 3。
  9. 由於 microTasks 佇列現在為空,事件循環檢查 MacroTaskQueue 並採取 () =>; console.log(6) 並在控制台中列印 6。
  10. 事件循環執行下一個任務() =>確保microTasks 佇列中沒有任何任務後,從macroTasks 中輸出console.log(5) 並在控制台中列印5 .
  11. 事件循環執行下一個任務 () =>來自 macroTasks 的 console.log(1) 並在控制台中列印 1。

感謝您的閱讀!我希望您覺得這個部落格內容豐富且引人入勝。如果您發現任何不準確之處或有任何回饋,請隨時告訴我。

以上是事件循環——JavaScript的詳細內容。更多資訊請關注PHP中文網其他相關文章!

來源:dev.to
本網站聲明
本文內容由網友自願投稿,版權歸原作者所有。本站不承擔相應的法律責任。如發現涉嫌抄襲或侵權的內容,請聯絡admin@php.cn
作者最新文章
熱門教學
更多>
最新下載
更多>
網站特效
網站源碼
網站素材
前端模板