记一道Promise then执行顺序的问题

65 阅读2分钟

Promise A+ 规范里 then 方法执行时,如果当前 promise 的状态是 fulfilled 或 rejected,会立即将对应的回调放到微任务队列里,如果当前 promise 的状态是 pending,则会将回调放到其对应的回调数组中,等到 promise 的状态确定后,再执行。

下面一段代码的执行结果是:01532476

Promise.resolve(console.log(0))             //  (1) 输出 0. resolve 内 立即执行,微任务空  这一步的 promise 为 o
  .then(() => {                             //  (2) 执行 then. (o fulfilled --> 回调直接加入微任务队列),这一步的 promise 为 a. 微任务包括 o 的 onfulfilled
                                            //   (5)  取出 o 的 onfulfilled 执行,微任务队列为空
    console.log(1)                          //  (6) 输出 1.
    Promise.resolve(console.log(5))         //   (7)  输出 5. resolve 立即执行,这一步的 promise 为 d
      .then(() => {                         //   (8)  执行 then. (d fulfilled --> 回调直接加入微任务队列), 这一步的 promise 为 e , 微任务队列包括 d 的 onfulfilled
        console.log(3)                      //   (12) 输出 3. 取出微任务 d 的 onfulfilled, 执行后微任务队列包括 b 的 onfulfilled
      })
      .then(() => {                         //   (9)  执行 then. (e pending --> e.fulfilledCallbacks.push), 这一步的 promise 为 f,微任务队列包括 d 的 onfulfilled
                                            //   (13) d resolve. 向微任务队列中 加入 f 的回调,微任务队列包括 b 的 onfulfilled 和 f 的 onfulfilled
        console.log(4)                      //   (16) 输出 4. 取出微任务 f 的 onfulfilled, 执行后微任务队列包括 c 的 onfulfilled
      })
      .then(() => {                         //   (10) 执行 then. (f pending --> f.fulfilledCallbacks.push), 这一步的 promise 为 g,微任务队列包括 c 的 onfulfilled
                                            //   (17)  f resolve. 向微任务队列中 加入 e 的回调, 微任务队列包括 c 的 onfulfilled 和 e 的 onfulfilled
        console.log(6)                      //   (18) 输出 6. 取出微任务 e 的 onfulfilled, 执行后微任务队列为空,执行完成
      })
  })
  .then(() => {                             //   (3)  执行 then. (a pending --> a.fulfilledCallbacks.push). 这一步的 promise 为 b,微任务包括 o 的 onfulfilled
                                            //   (11) a resolve. 向微任务队列中 加入 b 的回调, 微任务队列包括 d 的 onfulfilled 和 b 的 onfulfilled
    console.log(2)                          //   (14) 输出 2. 取出微任务 b 的 onfulfilled, 执行后微任务队列包括 f 的 onfulfilled
  })
  .then(() => {                             //   (4)  执行 then. (b pending --> b.fulfilledCallbacks.push),这一步的 promise 为 c, 微任务包括 o 的 onfulfilled. 开始执行微任务
                                            //   (15) b resolve  向微任务队列中 加入 c 的回调,执行后微任务队列包括 f 的 onfulfilled 和 c 的 onfulfilled
    console.log(7)                          //   (18) 输出 7. 取出微任务 c 的 onfulfilled, 执行后微任务队列为 e 的 onfulfilled
  })

image.png

image.png

image.png