------搞懂 Event Loop,你也能成为"异步忍者"
1. 引子:Node.js为什么这么快?
如果你第一次接触Node.js,
肯定听过一句吹爆的话:
"Node.js 是单线程,却能扛百万并发!"
听起来像开挂?
实际上,这全靠一个神奇的机制 ------ Event Loop(事件循环)。
搞懂 Event Loop,
你就能明白为什么 Node.js 能做到"不慌不忙,游刃有余",
哪怕面对成千上万个请求。
2. 什么是 Event Loop?
一句话解释:
Node.js用一个线程,在不停地"排队处理任务"。排队规则,就是Event Loop。
想象Node.js是一位神经大条又手速极快的服务员:
- 有顾客点单?记下来,排队。
- 菜做好了?叫顾客来拿。
- 有人催单?也记下来,一会儿处理。
- 总之:一件事一件事处理,绝不并发,绝不混乱。
**关键是:**它处理得又快又稳,大部分顾客都没感觉到排队了!
3. Node.js 中任务怎么分类?
Node.js把任务分成了两大类:
任务类型 | 举例 | 特点 |
---|---|---|
宏任务(Macro-task) | setTimeout 、setInterval 、I/O操作 |
每轮循环执行一个宏任务 |
微任务(Micro-task) | Promise.then 、process.nextTick |
当前宏任务完成后立刻执行,执行优先级更高 |
一句话:
微任务是"顺带处理",宏任务是"下次再处理"。
4. Event Loop的工作流程
大致步骤:
- 先执行当前宏任务(比如最开始的
main()
脚本) - 遇到Promise、nextTick?先记着,稍后处理
- 宏任务执行完 → 立刻清空微任务队列
- 微任务清空完 → 进入下一轮宏任务
- 重复循环!
来个流程图理解一下:
javascript
┌───────────────────────┐
│ 执行同步代码(主线程任务) │
└───────────────────────┘
↓
┌───────────────────────┐
│ 处理所有微任务(Promise、nextTick) │
└───────────────────────┘
↓
┌───────────────────────┐
│ 取下一个宏任务(setTimeout、I/O) │
└───────────────────────┘
↓
(重复循环,直到任务队列清空)
微任务 vs 宏任务的执行优先级
javascript
主线程代码执行完 →
↓
先清空 微任务队列(Promise、nextTick)
↓
然后取 宏任务 队列的第一个任务(setTimeout等)
就像一列高铁,每到一站(宏任务),顺便在站台(微任务)上处理点小事。
5. 举个经典例子(别说你懂Promise)
看下面这个例子,猜输出顺序:
javascript
console.log('start');
setTimeout(() => {
console.log('setTimeout');
}, 0);
Promise.resolve().then(() => {
console.log('promise');
});
console.log('end');
你猜结果是? 👇正确输出:
arduino
start
end
promise
setTimeout
解释:
start
同步执行end
同步执行Promise.then
是微任务,同步任务完成后立即执行setTimeout
是宏任务,下一轮Event Loop执行
6. 再讲一个Node.js的独门绝技:process.nextTick
Node.js还有个"超级微任务",叫 process.nextTick()
,
它比普通Promise还快,属于**"本轮循环必须立刻干的事"**。
看这个例子:
javascript
console.log('start');
process.nextTick(() => {
console.log('nextTick');
});
Promise.resolve().then(() => {
console.log('promise');
});
console.log('end');
输出顺序是:
arduino
start
end
nextTick
promise
👉 记住:
process.nextTick > Promise微任务 > 宏任务
arduino
执行顺序:
同步任务
↓
process.nextTick 回调
↓
Promise.then 回调
↓
宏任务(定时器等)
7. 为什么要理解Event Loop?
现实开发中,如果你不了解Event Loop,会踩无数坑,比如:
场景 | 可能出的问题 |
---|---|
异步顺序处理错误 | 结果顺序乱套 |
内存泄漏 | 微任务无限堆积 |
卡死主线程 | Promise链爆炸 |
性能瓶颈排查困难 | 不知道I/O卡在哪 |
懂了Event Loop,就能:
- 正确安排异步执行顺序
- 避免阻塞主线程
- 写出又快又稳的Node.js程序
8. 小总结
Event Loop 本质上是:
一个不断执行宏任务 → 清空微任务 → 再执行宏任务的无限循环。
Node.js通过这种机制,单线程也能做到高并发 ,
优雅又强大,
就像忍者一样 ------ 悄无声息地干掉成千上万的任务。
9. 彩蛋:一句话记住异步顺序
给你个最简单的记忆口诀:
同步代码先跑完,nextTick紧跟上,Promise接着来,最后轮到定时器。
arduino
同步代码先执行
↓
process.nextTick 优先处理
↓
Promise.then 再处理
↓
setTimeout 等宏任务最后处理
背下来,以后异步顺序题目轻松拿下!