JavaScript通过事件循环实现异步非阻塞,执行栈为空时先清空微任务队列再取宏任务;例如console.log同步执行,Promise.then入微任务,setTimeout入宏任务,输出顺序为1→4→3→2。

JavaScript 是单线程语言,意味着它在同一时间只能执行一个任务。为了处理异步操作(比如定时器、网络请求、DOM 事件等)而不阻塞主线程,JS 引入了事件循环(Event Loop)机制。理解事件循环是掌握异步编程的关键。
JS 的代码执行依赖于执行栈(Call Stack),它是一个后进先出的结构,用于追踪函数的调用顺序。当函数被调用时,它会被压入栈中;执行完毕后,从栈中弹出。
然而,像 setTimeout、fetch 或 addEventListener 这类异步操作并不会立即进入执行栈。它们会被交给浏览器的其他模块(如定时器模块、HTTP 模块)处理,完成后将对应的回调函数推入任务队列(Task Queue)。
常见的任务队列分为:
立即学习“Java免费学习笔记(深入)”;
事件循环的核心职责是不断检查执行栈是否为空,一旦为空,就从任务队列中取出最早的任务推入执行栈执行。但它有一个优先级规则:
console.log('1');
setTimeout(() => {
console.log('2');
}, 0);
Promise.resolve().then(() => {
console.log('3');
});
console.log('4');
输出顺序是:1 → 4 → 3 → 2。因为:
理解两者的执行时机有助于避免一些异步陷阱。例如:
Promise.resolve().then(() => {
console.log('微任务1');
process.nextTick(() => console.log('Node中的微任务'));
Promise.resolve().then(() => console.log('嵌套微任务'));
});
console.log('同步任务');
在 Node.js 环境中,输出为:同步任务 → 微任务1 → 嵌套微任务 → Node中的微任务。这说明微任务会按队列顺序执行,且嵌套的微任务也会被追加并及时处理。
在浏览器中,queueMicrotask 提供了一种显式添加微任务的方式,常用于延迟执行但又希望快于下一轮渲染的操作。
浏览器的 UI 渲染也是一个宏任务。通常,每轮事件循环结束后,如果需要更新界面,浏览器会在合适的时机进行渲染。但由于微任务会在渲染前全部执行完,因此长时间运行的微任务会阻塞页面渲染。
所以,大量异步更新应优先使用宏任务(如 setTimeout)来让出控制权,避免界面卡顿。
基本上就这些。事件循环虽小,却是异步行为的基石。搞清楚宏任务和微任务的执行顺序,能让你写出更可预测的 JavaScript 代码。不复杂,但容易忽略细节。
以上就是JS事件循环机制_深入理解JavaScript异步编程的详细内容,更多请关注php中文网其它相关文章!
编程怎么学习?编程怎么入门?编程在哪学?编程怎么学才快?不用担心,这里为大家提供了编程速学教程(入门课程),有需要的小伙伴保存下载就能学习啦!
Copyright 2014-2025 https://www.php.cn/ All Rights Reserved | php.cn | 湘ICP备2023035733号