事件循环:
- 同步和异步任务分别进入不同的执行"场所",同步的进入主线程,异步的进入Event Table并注册函数
- 当指定的事情完成时,Event Table会将这个函数移入Event Queue
- 主线程内的任务执行完毕为空,会去Event Queue读取对应的函数,进入主线程执行
console.log(1);
setTimeout(() => {
console.log(2);
}, 0);
console.log(3);
// 1 3 2
宏任务和微任务
不同的异步事件,会进入不同的Event Queue,进一步把异步事件划分为宏任务和微任务
- 宏任务主要有:setTimeout、setInterval、I/O、script代码块等
- 微任务的主要有:nextTick、callback、Promise、process.nextTick等
执行顺序
进入整体代码(宏任务)后,开始第一次循环。接着执行所有的微任务。然后再次从宏任务开始,找到其中一个任务队列执行完毕,再执行所有的微任务。
例子1:在同一个按钮上绑定两个点击事件,用户点击按钮,输出的顺序是什么?
button.addEventListener('click',() => {
Promise.resolve().then(() => console.log('Promise 1'))
console.log('Listener 1')
})
button.addEventListener('click',() => {
Promise.resolve().then(() => console.log('Promise 2'))
console.log('Listener 2')
})
// button.click() // 如果使用js代码执行点击事件,输出结果会有变化吗
输出结果是
Listener 1 Promise 1 Listener 2 Promise 2
参考:
https://juejin.im/post/6844904198581010439#heading-13