任务执行机制(事件循环EventLoop) - 图1

理解js里面的任务执行机制

相关概念

  • 异步编程
  • Javascript的事件循环
  • 任务队列
  • 微任务队列
  • ……

以下代码执行的结果是什么?

  1. console.log(1);
  2. setTimeout(function () {
  3. console.log(3);
  4. }, 3000);
  5. console.log(2);

image.png
以下代码执行的结果是什么?

  1. console.log(1);
  2. setTimeout(function () {
  3. console.log(3);
  4. }, 0);
  5. console.log(2);

image.png

啥是单线程

任务执行机制(事件循环EventLoop) - 图4
单线程就意味着,所有任务需要排队,前一个任务结束,才会执行后一个任务。如果前一个任务耗时很长,后一个任务就不得不一直等着。
这样所导致的问题是: 如果 JS 执行的时间过长,这样就会造成页面的渲染不连贯,导致页面渲染加载阻塞的感觉。

同步任务和异步任务

  1. 单线程导致的问题就是后面的任务等待前面任务完成,如果前面任务很耗时(比如读取网络数据),后面任务不得不一直等待!!<br /> 为了解决这个问题,利用多核 CPU 的计算能力,HTML5 提出 Web Worker 标准,允许 JavaScript 脚本创建多个线程,但是子线程完全受主线程控制。于是,JS 中出现了**同步任务**和**异步任务**。

任务执行机制(事件循环EventLoop) - 图5操作系统忘完了

JS中所有任务可以分成两种,一种是同步任务(synchronous),另一种是异步任务(asynchronous)。
【同步任务】指的是:
在主线程上排队执行的任务,只有前一个任务执行完毕,才能执行后一个任务;
【异步任务】指的是:
不进入主线程、而进入“任务队列”的任务,当主线程中的任务运行完了,才会从”任务队列”取出异步任务放入主线程执行。
任务执行机制(事件循环EventLoop) - 图6

JS执行机制(事件循环)

任务执行机制(事件循环EventLoop) - 图7
任务执行机制(事件循环EventLoop) - 图8
任务执行机制(事件循环EventLoop) - 图9

例子

  1. console.log("主线程:第一个");
  2. document.onclick = function() {
  3. console.log('点击事件开始');
  4. }
  5. setTimeout(function() {
  6. console.log("定时器3s");
  7. }, 3000)
  8. setTimeout(function() {
  9. console.log("定时器1s");
  10. }, 1000)
  11. console.log("主线程:最后一个");

image.png
image.png

JS创建异步任务枚举

参考:

期约Promise

调用栈、消息队列、微任务队列

  • 调用栈:遇到函数调用就把函数压入栈内
  • 消息队列(宏任务):
  • 微任务队列:

Promise、Async、await不是很理解
参考:

console.log(‘script start’)

setTimeout(() => { console.log(‘setTimeout’) }, 0)

Promise.resolve().then(() => { console.log(‘promise1’) })

a1()

let promise2 = new Promise((resolve) => { resolve(‘promise2.then’) console.log(‘promise2’) })

promise2.then((res) => { console.log(res) Promise.resolve().then(() => { console.log(‘promise3’) }) }) console.log(‘script end’) ``` image.png