起因

明天遇到一个题目,钻研了一天,从新复习了一遍Promise实现,得进去一个不算论断的论断......

这个题通过我的化简长成这样,求代码后果

const p = Promise.resolve()new Promise(resolve => {     new Promise(resolve => {resolve(p)})     .then(() => {         console.log('after:await')     })})let p1 = p.then(() => {    console.log('tick:a')})let p2 = p1.then(() => {    console.log('tick:b')})let p3 = p2.then(() => {    console.log('tick:c')})/*p.then(() => {    console.log('tick:a')}).then(() => {    console.log('tick:b')}).then(() => {    console.log('tick:c')})*/

promise本质

咱们晓得excutor同步执行,then外面的代码异步执行,怎么实现的?
简略的说(这里以胜利为例),then外面的代码同步增加到所属promise的胜利回调队列,当excutor外面的参数resolve办法执行的时候,会把胜利回调队列外面的代码顺次执行

对resolve参数的解决

如果excutor的resolve办法承受的参数是一个Promise对象会怎么样?
首先我在promiseA+标准外面并没有找到这种状况的规定

而后我看了三个promise库,bluebird,es6-promise,promise,都没有对这种状况作解决,也就是当成一个一般的对象

最初阮一峰的es6外面对这种状况有形容

resolve函数的参数除了失常的值以外,还可能是另一个 Promise 实例,这时p1的状态就会传递给p2,p2的回调函数就会期待p1的状态扭转

应该是新增加的Promise的规定

已有的材料的相干实现

在网上看了很多Promise实现,根本对promise的excutor的resolve办法的实现是这样的promise实现。对参数如果是Promise都是等promise执行完再调resolve

constructor(executor){       ...        let resolve = (value) =>{ // 如果resolve的值时一个promise            if(value instanceof Promise){                // 我就让这个promise执行,把胜利的后果再次判断                return value.then(resolve,reject) //参数会主动传递到resolve外面去            }            if (this.status === 'pending') {                this.status = 'fulfilled'                this.value = value                this.onFulfilledCallback.forEach(fn => fn(this.value))            }                   }        ...

留神,这种实现能跑过PromiseA+标准测试用例!从A+标准的角度没有问题

问题呈现

下面的实现相当于让咱们的题目中的p执行完后再resolve,我转换一下题目局部,你们就很分明了

new Promise(resolve => {     new Promise(resolve => {        //resolve(p)        //相当于变成了        p.then(resolve)     })     .then(() => {         console.log('after:await')     })})

看起来很对,执行后果是
tick:a
after:await
tick:b
tick:c

然而咱们如果用原生Promise,理论执行后果是
tick:a
tick:b
after:await
tick:c

论断

貌似目前的promise在resolve参数解决上和a+标准上的不太一样
如果面试做题遇到的话,求执行程序,如果参数是一个Promsie实例i,我倡议这么解决。具体起因不晓得,晓得的大佬留言区通知我一声

var p = Promise.resolve()new Promise(resolve => {     new Promise(resolve => {        //resolve(p)        //相当于变成了        p.then().then(resolve)     })     .then(() => {         console.log('after:await')     })})