关于前端:Promiseresolve与new-Promiseresolveresolve的区别

35次阅读

共计 1901 个字符,预计需要花费 5 分钟才能阅读完成。

参考:

  • Promise.resolve() 与 new Promise(r => r(v))
  • new Promise((resolve)=>{resolve()}) 与 Promise.resolve() 等价吗
  • 探讨:当 Async/Await 的遇到了 EventLoop

返回值

如果参数是 promise 实例,前者返回新期约,后者原样返回:


let p = new Promise((r)=>{r("123")})

//Promise.resolve 将一成不变返回这个实例
p === Promise.resolve(p)  //true


//new Promise() 返回一个新期约
let p2 = new Promise((r)=>{r(p)
})

p2 !== p    //true

参数是一个 thenable 对象, 都返回新的解决期约:

let thenable = {then: function(resolve,reject){resolve("123")
  }
}

let p1 = new Promise((r)=>{//p1: Promise {<fulfilled>: "123"}
  r(thenable)
})

let p2 = Promise.resolve(thenable)  //p2:  Promise {<fulfilled>: "123"}

then 的执行机会

new Promise(r => r(v)) 的 then() 回调会被推延两个时序(事件循环):

console.log("script start")

let v = new Promise((resolve)=>{console.log("v start")
  resolve("v resolve")
})

let p1 = new Promise((resolve)=>{console.log(1)
  resolve(v)
}).then((v)=>{console.log(v)
})

new Promise((resolve)=>{resolve()
}).then(()=>{console.log(2)
}).then(()=>{console.log(3)
}).then(()=>{console.log(4)
}).then(()=>{console.log(5)
})


console.log("script end")

//"script start"
//"v start"
//1
//"script end"
//2
//3
//v resolve   推延了两个循环
//4
//5

而 Promise.resolve(v) 都 then() 则失常:

console.log("script start")

let v = new Promise((resolve)=>{console.log("v start")
  resolve("v resolve")
})

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

new Promise((resolve)=>{resolve()
}).then(()=>{console.log(2)
}).then(()=>{console.log(3)
}).then(()=>{console.log(4)
}).then(()=>{console.log(5)
})


console.log("script end")

//"script start"
//"v start"
//"script end"
//"v resolve"
//2
//3
//4
//5

起因:

  • 这是因为浏览器发现 resolve 的是另一个 promise 时(假如称原 promise 为 promiseA,另一个 promise 为 promiseB),会创立一个名为 PromiseResolveThenableJob 的工作去解决 promiseB,而这个工作是一个微工作
  • 等到 promiseB 被 resolved 之后,会再生成去解决 promiseA(resolvePromiseA)的微工作
  • 执行完 resolvePromiseA 微工作,才会执行 promiseA 的 then,因而推延了两个事件循环
  • 而 Promise.resolve() 的 then 失常执行,是因为参数是 promiseB 时,会不做解决返回 promiseB 自身

能够用伪代码将 PromiseResolveThenableJob 示意为:

let promiseA = new Promise((resolve)=>{resolve(promiseB)
}).then(()=>{console.log("123")
})

//PromiseResolveThenableJob 的伪代码,能够了解成
promiseB.then(()=>{
  resolvePromiseA,
  rejectPromiseA
})

正文完
 0