前端面试宝典

第 1 题(入门必考题)

console.log(1);

setTimeout(() => {
  console.log(2);
}, 0);

Promise.resolve().then(() => {
  console.log(3);
});

console.log(4);

输出顺序:

1 4 3 2

解析:

  1. 先执行同步代码14
  2. 再执行所有微任务Promise.then → 3
  3. 最后执行宏任务setTimeout → 2

第 2 题(带 Promise 嵌套,高频)

console.log(1);

setTimeout(() => {
  console.log(2);
  Promise.resolve().then(() => {
    console.log(3);
  });
}, 0);

Promise.resolve().then(() => {
  console.log(4);
});

console.log(5);

输出顺序:

1 5 4 2 3

解析:

  1. 同步:15
  2. 微任务:Promise.then → 4
  3. 宏任务:setTimeout → 2
    • 执行宏任务内部时,遇到新的微任务 3立即执行

第 3 题(综合最难,面试压轴)

async function async1() {
  console.log(1);
  await async2();
  console.log(2);
}

async function async2() {
  console.log(3);
}

console.log(4);

setTimeout(() => {
  console.log(5);
}, 0);

async1();

new Promise(resolve => {
  console.log(6);
  resolve();
}).then(() => {
  console.log(7);
});

console.log(8);

输出顺序:

4 1 3 6 8 2 7 5

我给你来 4 道进阶版 Event Loop 面试题,包含:
async/await、Promise 嵌套、微任务套微任务、宏任务套宏任务,前端面试最难也就这样了

你可以先自己做,再看答案解析。


第 4 题(微任务套微任务,经典坑)

Promise.resolve()
  .then(() => {
    console.log(1);
    Promise.resolve().then(() => {
      console.log(2);
    });
  })
  .then(() => {
    console.log(3);
  });

setTimeout(() => {
  console.log(4);
}, 0);

答案:1 2 3 4

解析:

  • 先清空所有微任务,再执行宏任务
  • 微任务里新加的微任务,会在本轮一起清空

第 5 题(await + 多层 Promise,大厂最爱)

async function fn() {
  console.log(1);
  await Promise.resolve();
  console.log(2);
  await Promise.resolve();
  console.log(3);
}

console.log(4);
fn();
console.log(5);

答案:4 1 5 2 3

解析:

  • await 前面:同步
  • await 后面:微任务
  • 多个 await 会按顺序进微任务队列

第 6 题(宏任务里套宏任务 + 微任务)

setTimeout(() => {
  console.log(1);
  setTimeout(() => {
    console.log(2);
  }, 0);
  Promise.resolve().then(() => {
    console.log(3);
  });
}, 0);

setTimeout(() => {
  console.log(4);
}, 0);

答案:1 3 4 2

解析:

  • 一次只执行一个宏任务
  • 执行完一个宏任务 → 清空微任务 → 再取下一个宏任务

第 7 题(综合地狱版,能做对就通关)

async function async1() {
  console.log(1);
  await async2();
  console.log(2);
}

async function async2() {
  console.log(3);
  Promise.resolve().then(() => {
    console.log(4);
  });
}

console.log(5);

setTimeout(() => {
  console.log(6);
}, 0);

async1();

new Promise((resolve) => {
  console.log(7);
  resolve();
}).then(() => {
  console.log(8);
});

console.log(9);

答案:5 1 3 7 9 4 2 8 6


最终铁律(背会这 4 条,所有题都稳)

  1. 同步代码最先执行
  2. 每执行一个宏任务,就清空所有微任务
  3. 微任务里新增的微任务,本轮一起执行完
  4. await 后面 = 微任务

一句话总结:同步先跑完,微任务全清,再跑一个宏,循环永不停。

关键知识点:

  • async 函数里 await 前面 是同步代码
  • await 后面的代码 = 微任务
  • new Promise(() => {}) 里是同步代码
  • .then() 是微任务