Event Loop

157 阅读1分钟

进程与线程

进程描述了 CPU 在运行指令及加载和保存上下文所需的时间,放在应用上来说就代表了一个程序。线程是进程中的最小单位,描述了执行一段指令所需的时间。

锁:只需要在读取的时候加锁,直到读取完毕之前都不能进行写入操作。

执行栈:存储函数调用的栈结构,遵循先进后出的原则

浏览器中的 Event Loop:其实当遇到异步的代码时,会被挂起并在需要执行的时候加入到 Task(有多种 Task) 队列中。一旦执行栈为空,Event Loop 就会从 Task 队列中拿出需要执行的代码并放入执行栈中执行

console.log('script start')

async function async1() {
  await async2()
  console.log('async1 end')
}
async function async2() {
  console.log('async2 end')
}
async1()

setTimeout(function() {
  console.log('setTimeout')
}, 0)

new Promise(resolve => {
  console.log('Promise')
  resolve()
})
  .then(function() {
    console.log('promise1')
  })
  .then(function() {
    console.log('promise2')
  })

console.log('script end')

script start
VM36:8 async2 end
VM36:17 Promise //async声明一个promise函数,自然触发new Promise(resolve => {
VM36:27 script end //同步执行完毕
VM36:5 async1 end
VM36:21 promise1
VM36:24 promise2
undefined
VM36:13 setTimeout

Event Loop 执行顺序如下所示:

首先执行同步代码,这属于宏任务
当执行完所有同步代码后,执行栈为空,查询是否有异步代码需要执行
执行所有微任务
当执行完所有微任务后,如有必要会渲染页面
然后开始下一轮 Event Loop,执行宏任务中的异步代码,也就是 setTimeout 中的回调函数

微任务包括 process.nextTick ,promise ,MutationObserver。

宏任务包括 script , setTimeout ,setInterval ,setImmediate ,I/O ,UI rendering。