参见:https://juejin.cn/post/6844903665686282253
const FULLFILLED='FULLFILLED'
const REJECTED='REJECTED'
const PENDDING='PENDDING'
class MyPromise{
constructor(handle){
//初始化状态
this._status=PENDDING
this._value=undefined
this.fullfilledQueues=[]
this.rejectedQueues=[]
try{
handle(this._resolve.bind(this),this.reject.bind(this))
}catch(e){
this._reject(e).bind(this)
}
}
_resolve(val){
if(_this._status!==PENDDING) return
const run=()=>{
this._status=FULLFILLED
this._value=val
let cb
while(cb=this.fullfilledQueues.shift()){
cb(val)
}
}
// 为了支持同步的Promise,这里采用异步调用
setTimeout(()=>run(),0)
}
//val 也有可能是 promise
_resolve2(val){
if(_this._status!==PENDDING) return
const run=()=>{
const runFullfill=(val)=>{
let cb
while(cb=this.fullfilledQueues.shift()){
cb(val)
}
}
const runReject=(val)=>{
let cb
while(cb=this.rejectedQueues.shift()){
cb(val)
}
}
if(val instanceof MyPromise){
val.then(res=>{
this._status=FULLFILLED
this._value=val
runFullfill(val)
},error=>{
this._status=REJECTED
this._value=error
runReject(error)
})
}else{
this._status=FULLFILLED
this._value=val
runFullfill(val)
}
}
// 为了支持同步的Promise,这里采用异步调用
setTimeout(()=>run(),0)
}
_reject(val){
if(_this._status!==PENDDING) return
this._status=REJECTED
this._value=val
let cb
while(cb=this.rejectedQueues.shift()){
cb(val)
}
}
then(onFullfilled,onRejected){
return new MyPromise((onFulfilledNext,onRejectedNext)=>{
let fullfilled=(value)=>{
let res=onFullfilled(value)
if(res instanceof MyPromise){
res.then(onFulfilledNext,onRejectedNext)
}else{
onFulfilledNext(res)
}
}
let rejected=(error)=>{
let res=onRejected(error)
if(res instanceof MyPromise){
res.then(onFulfilledNext,onRejectedNext)
}else{
onRejectedNext(res)
}
}
switch(this._status){
case PENDING:
this._fulfilledQueues.push(onFullfilled)
this._rejectedQueues.push(onRejected)
break
// 当状态已经改变时,立即执行对应的回调函数
case FULFILLED:
fullfilled(this._value)
break
case REJECTED:
rejected(this._value)
break
}
})
}
//相当于调用 then 方法, 但只传入 Rejected 状态的回调函数
catch(onRejected){
return this.then(undefined,onRejected)
}
//Promise.all()方法用于将多个 Promise 实例,包装成一个新的 Promise 实例 p。
//只有全部状态都变成fulfilled,p的状态才会变成fulfilled
//只要其中有一个被rejected,p的状态就变成rejected
static all(list){
return new MyPromise((resolve,reject)=>{
let count=0
let values=[]
for(let i=0;i<list.length;i++){
let p=list[i]
//如果p不是promise对象,则需要转换一下
//p=MyPromise.resolve(p)
p.then(res=>{
count++
values[i]=res
if(count===list.length){
resolve(values)
}
},err=>{
reject(err)
})
}
})
}
//Promise.race()方法用于将多个 Promise 实例,包装成一个新的 Promise 实例 p。
//只要其中有一个率先改变状态,p的状态就跟着改变
//率先改变的 Promise 实例的返回值,就传递给p的回调函数
static race(list){
return new MyPromise((resolve,reject)=>{
list.forEach(element => {
element.then(res=>{
resolve(res)
},err=>{
reject(err)
})
});
})
}
static resolve(val){
if(val instanceof MyPromise){
return val
}else{
return new MyPromise((resolve)=>{
resolve(val)
})
}
}
static reject(val){
return new MyPromise((resolve,reject)=>{
reject(val)
})
}
}