乐趣区

关于javascript:实现Promise的原型方法前端面试能力提升

说起 Promise 大家应该都耳熟能详,咱们明天来看下 Promise 的相干办法

有如下:
原型办法:then、catch、finally

静态方法:resolve、reject、race、all、allSettled、any

手写实现办法如下:

实现 resolve 办法

promise.resolve('123')本质上就是
new Promise(resolve=>
resolve('123')
})

Promise.resolve(value) 将给定的一个值转为 Promise 对象。

  • 如果这个值是一个 promise,那么将返回这个 promise;
  • 如果这个值是 thenable(即带有 ”then” 办法),返回的 promise 会“追随”这个 thenable 的对象,采纳它的最终状态;
  • 否则返回的 promise 将以此值实现,即以此值执行 resolve()办法 (状态为 fulfilled)。
 class MyPromise {
        static PENDING = 'pending'
        static FULFILLED = 'fulfilled'
        static REJECTED = 'rejected'
        constructor(executor) {
          this.PromiseState = MyPromise.PENDING
          this.PromiseResult = null
          this.fulfilledCallBacks = []
          this.rejectedCallBacks = []
          try {executor(this.resolve.bind(this), this.reject.bind(this))
          } catch (error) {this.reject(error)
          }
        }
        resolve(result) {if ((this.PromiseState = MyPromise.PENDING)) {setTimeout(() => {
              this.PromiseState = MyPromise.FULFILLED
              this.PromiseResult = result
              for (const callBack of this.fulfilledCallBacks) {callBack(result)
              }
            })
          }
        }
        reject(reason) {if ((this.PromiseState = MyPromise.PENDING)) {setTimeout(() => {
              this.PromiseState = MyPromise.REJECTED
              this.PromiseResult = reason
              for (const callBack of this.rejectedCallBacks) {callBack(reason)
              }
            })
          }
        }
        then(onFulfilled, onRejected) {
          onFulfilled =
            typeof onFulfilled === 'function' ? onFulfilled : (val) => val
          onRejected =
            typeof onRejected === 'function'
              ? onRejected
              : (err) => {throw err}
          return new MyPromise((resolve, reject) => {if (this.PromiseState === MyPromise.PENDING) {this.fulfilledCallBacks.push(() => {setTimeout(() => {let x = onFulfilled(this.PromiseResult)
                  x instanceof MyPromise ? x.then(resolve, reject) : resolve(x)
                })
              })
              this.rejectedCallBacks.push(() => {setTimeout(() => {let x = onRejected(this.PromiseResult)
                  x instanceof MyPromise ? x.then(resolve, reject) : reject(x)
                })
              })
            } else if (this.PromiseState === MyPromise.FULFILLED) {
              try {setTimeout(() => {let x = onFulfilled(this.PromiseResult)
                  x instanceof MyPromise ? x.then(resolve, reject) : resolve(x)
                })
              } catch (error) {reject(error)
              }
            } else {
              try {setTimeout(() => {let x = onRejected(this.PromiseResult)
                  x instanceof MyPromise ? x.then(resolve, reject) : reject(x)
                })
              } catch (error) {reject(error)
              }
            }
          })
        }
        //value 要解析为 Promise 对象的值
        static resolve(value) {
          // 如果是
          if (value instanceof MyPromise) {return value} else if (value && typeof value === 'object' && 'then' in value) {return new MyPromise((resolve, reject) => {value.then(resolve, reject)
            })
          }
          return new MyPromise((resolve) => {resolve(value)
          })
        }
      }
      const promise1 = MyPromise.resolve(123)

      promise1.then((value) => {console.log(value)
        // expected output: 123
      })

      // Resolve 一个 thenable 对象
      var p1 = MyPromise.resolve({then: function (onFulfill) {onFulfill('Resolving')
        },
      })
      console.log(p1 instanceof MyPromise) // true, 这是一个 Promise 对象

      setTimeout(() => {console.log('p1 :>>', p1)
      }, 1000)

      p1.then(function (v) {console.log(v) // 输入 "Resolving!"
        },
        function (e) {// 不会被调用}
      )

      // Thenable 在 callback 之前抛出异样
      // MyPromise rejects
      var thenable = {then: function (resolve) {throw new TypeError('Throwing')
          resolve('Resolving')
        },
      }

      var p2 = MyPromise.resolve(thenable)
      p2.then(function (v) {// 不会被调用},
        function (e) {console.log(e) // TypeError: Throwing
        }
      )
更多面试题解答参见 前端手写面试题具体解答

实现 reject 办法

const p=Promise.reject(‘error’)
相当于下方函数:
const p=new Promise(reject=>{
reject(‘11111’)
})

Promise.reject()办法返回一个带有回绝起因的 Promise 对象。

 class MyPromise {
        static PENDING = 'pending'
        static FULFILLED = 'fulfilled'
        static REJECTED = 'rejected'
        constructor(executor) {
          this.PromiseState = MyPromise.PENDING
          this.PromiseResult = null
          this.fulfilledCallBacks = []
          this.rejectedCallBacks = []
          try {executor(this.resolve.bind(this), this.reject.bind(this))
          } catch (error) {this.reject(error)
          }
        }
        resolve(result) {if ((this.PromiseState = MyPromise.PENDING)) {setTimeout(() => {
              this.PromiseState = MyPromise.FULFILLED
              this.PromiseResult = result
              for (const callBack of this.fulfilledCallBacks) {callBack(result)
              }
            })
          }
        }
        reject(reason) {if ((this.PromiseState = MyPromise.PENDING)) {setTimeout(() => {
              this.PromiseState = MyPromise.REJECTED
              this.PromiseResult = reason
              for (const callBack of this.rejectedCallBacks) {callBack(reason)
              }
            })
          }
        }
        then(onFulfilled, onRejected) {
          onFulfilled =
            typeof onFulfilled === 'function' ? onFulfilled : (val) => val
          onRejected =
            typeof onRejected === 'function'
              ? onRejected
              : (err) => {throw err}
          return new MyPromise((resolve, reject) => {if (this.PromiseState === MyPromise.PENDING) {this.fulfilledCallBacks.push(() => {setTimeout(() => {let x = onFulfilled(this.PromiseResult)
                  x instanceof MyPromise ? x.then(resolve, reject) : resolve(x)
                })
              })
              this.rejectedCallBacks.push(() => {setTimeout(() => {let x = onRejected(this.PromiseResult)
                  x instanceof MyPromise ? x.then(resolve, reject) : reject(x)
                })
              })
            } else if (this.PromiseState === MyPromise.FULFILLED) {
              try {setTimeout(() => {let x = onFulfilled(this.PromiseResult)
                  x instanceof MyPromise ? x.then(resolve, reject) : resolve(x)
                })
              } catch (error) {reject(error)
              }
            } else {
              try {setTimeout(() => {let x = onRejected(this.PromiseResult)
                  x instanceof MyPromise ? x.then(resolve, reject) : reject(x)
                })
              } catch (error) {reject(error)
              }
            }
          })
        }
        //error 要解析为 Promise reject 的值
        static reject(error) {return new MyPromise((resolve, reject) => {reject(error)
          })
        }
      }
      MyPromise.reject(new Error('fail')).then(function () {// not called},
        function (error) {console.error(error) // Error: fail
        }
      )

实现 Promise.prototype.catch 办法

catch() 办法返回一个 Promise,并且解决回绝的状况,用于指定产生谬误时的回调函数。

它的行为与调用 Promise.prototype.then(undefined, onRejected) 雷同。

class MyPromise {
    static PENDING = 'pending'
    static FULFILLED = 'fulfilled'
    static REJECTED = 'rejected'
    constructor(executor) {
        this.PromiseState = MyPromise.PENDING
        this.PromiseResult = null
        this.fulfilledCallBacks = []
        this.rejectedCallBacks = []
        try {executor(this.resolve.bind(this), this.reject.bind(this))
        } catch (error) {this.reject(error)
        }
    }
    resolve(result) {if ((this.PromiseState = MyPromise.PENDING)) {setTimeout(() => {
                this.PromiseState = MyPromise.FULFILLED
                this.PromiseResult = result
                for (const callBack of this.fulfilledCallBacks) {callBack(result)
                }
            })
        }
    }
    reject(reason) {if ((this.PromiseState = MyPromise.PENDING)) {setTimeout(() => {
                this.PromiseState = MyPromise.REJECTED
                this.PromiseResult = reason
                for (const callBack of this.rejectedCallBacks) {callBack(reason)
                }
            })
        }
    }
    then(onFulfilled, onRejected) {
        onFulfilled =
            typeof onFulfilled === 'function' ? onFulfilled : (val) => val
        onRejected =
            typeof onRejected === 'function'
            ? onRejected
            : (err) => {throw err}
        return new MyPromise((resolve, reject) => {if (this.PromiseState === MyPromise.PENDING) {this.fulfilledCallBacks.push(() => {setTimeout(() => {let x = onFulfilled(this.PromiseResult)
                        x instanceof MyPromise ? x.then(resolve, reject) : resolve(x)
                    })
                })
                this.rejectedCallBacks.push(() => {setTimeout(() => {let x = onRejected(this.PromiseResult)
                        x instanceof MyPromise ? x.then(resolve, reject) : reject(x)
                    })
                })
            } else if (this.PromiseState === MyPromise.FULFILLED) {
                try {setTimeout(() => {let x = onFulfilled(this.PromiseResult)
                        x instanceof MyPromise ? x.then(resolve, reject) : resolve(x)
                    })
                } catch (error) {reject(error)
                }
            } else {
                try {setTimeout(() => {let x = onRejected(this.PromiseResult)
                        x instanceof MyPromise ? x.then(resolve, reject) : reject(x)
                    })
                } catch (error) {reject(error)
                }
            }
        })
    }
    catch(onRejected) {return this.then(undefined, onRejected)
    }
}

// 捕捉异样
const p2 = new MyPromise(function (resolve, reject) {throw new Error('test')
})
p2.catch(function (error) {console.log(error) //Error: test
})

实现 Promise.prototype.finally

finally() 办法返回一个 Promise。在 promise 完结时,无论后果是 fulfilled 或者是 rejected,都会执行指定的回调函数。

因为无奈晓得 promise 的最终状态,所以 finally 的回调函数中不接管任何参数,它仅用于无论最终后果如何都要执行的状况。

   class MyPromise {
        static PENDING = 'pending'
        static FULFILLED = 'fulfilled'
        static REJECTED = 'rejected'
        constructor(executor) {
          this.PromiseState = MyPromise.PENDING
          this.PromiseResult = null
          this.fulfilledCallBacks = []
          this.rejectedCallBacks = []
          try {executor(this.resolve.bind(this), this.reject.bind(this))
          } catch (error) {this.reject(error)
          }
        }
        resolve(result) {if ((this.PromiseState = MyPromise.PENDING)) {setTimeout(() => {
              this.PromiseState = MyPromise.FULFILLED
              this.PromiseResult = result
              for (const callBack of this.fulfilledCallBacks) {callBack(result)
              }
            })
          }
        }
        reject(reason) {if ((this.PromiseState = MyPromise.PENDING)) {setTimeout(() => {
              this.PromiseState = MyPromise.REJECTED
              this.PromiseResult = reason
              for (const callBack of this.rejectedCallBacks) {callBack(reason)
              }
            })
          }
        }
        then(onFulfilled, onRejected) {
          onFulfilled =
            typeof onFulfilled === 'function' ? onFulfilled : (val) => val
          onRejected =
            typeof onRejected === 'function'
              ? onRejected
              : (err) => {throw err}
          return new MyPromise((resolve, reject) => {if (this.PromiseState === MyPromise.PENDING) {this.fulfilledCallBacks.push(() => {setTimeout(() => {let x = onFulfilled(this.PromiseResult)
                  x instanceof MyPromise ? x.then(resolve, reject) : resolve(x)
                })
              })
              this.rejectedCallBacks.push(() => {setTimeout(() => {let x = onRejected(this.PromiseResult)
                  x instanceof MyPromise ? x.then(resolve, reject) : reject(x)
                })
              })
            } else if (this.PromiseState === MyPromise.FULFILLED) {
              try {setTimeout(() => {let x = onFulfilled(this.PromiseResult)
                  x instanceof MyPromise ? x.then(resolve, reject) : resolve(x)
                })
              } catch (error) {reject(error)
              }
            } else {
              try {setTimeout(() => {let x = onRejected(this.PromiseResult)
                  x instanceof MyPromise ? x.then(resolve, reject) : reject(x)
                })
              } catch (error) {reject(error)
              }
            }
          })
        }
        finally(callBack) {return this.then(callBack, callBack)
        }
      }

      // 捕捉异样
      let p1 = new MyPromise(function (resolve, reject) {resolve(1)
      }).finally(function () {console.log('finally') // finally
        })

实现 Promise.all

Promise.all() 办法接管一个 promise 的 iterable 类型(注:Array,Map,Set 都属于 ES6 的 iterable 类型)的输出,并且只返回一个 Promise 实例,输出的所有 promise 的 resolve 回调的后果是一个数组。

  • Promise.all 期待所有都实现(或第一个失败)
  • 如果传入的参数是一个空的可迭代对象,则返回一个已实现(already resolved)状态的 Promise
  • 如果参数中蕴含非 promise 值,这些值将被疏忽,但依然会被放在返回数组中,如果 promise 实现的话 (也就是如果参数里的某值不是 Promise,则须要原样返回在数组里)
  • 在任何状况下,Promise.all 返回的 promise 的实现状态的后果都是一个数组,它蕴含所有的传入迭代参数对象的值(也包含非 promise 值)。
  • 如果传入的 promise 中有一个失败(rejected),Promise.all 异步地将失败的那个后果给失败状态的回调函数,而不论其它 promise 是否实现
class MyPromise {
  static PENDING = 'pending'
  static FULFILLED = 'fulfilled'
  static REJECTED = 'rejected'
  constructor(executor) {
    this.PromiseState = MyPromise.PENDING
    this.PromiseResult = null
    this.fulfilledCallBacks = []
    this.rejectedCallBacks = []
    try {executor(this.resolve.bind(this), this.reject.bind(this))
    } catch (error) {this.reject(error)
    }
  }
  resolve(result) {if ((this.PromiseState = MyPromise.PENDING)) {setTimeout(() => {
        this.PromiseState = MyPromise.FULFILLED
        this.PromiseResult = result
        for (const callBack of this.fulfilledCallBacks) {callBack(result)
        }
      })
    }
  }
  reject(reason) {if ((this.PromiseState = MyPromise.PENDING)) {setTimeout(() => {
        this.PromiseState = MyPromise.REJECTED
        this.PromiseResult = reason
        for (const callBack of this.rejectedCallBacks) {callBack(reason)
        }
      })
    }
  }
  then(onFulfilled, onRejected) {
    onFulfilled =
      typeof onFulfilled === 'function' ? onFulfilled : (val) => val
    onRejected =
      typeof onRejected === 'function'
      ? onRejected
      : (err) => {throw err}
    return new MyPromise((resolve, reject) => {if (this.PromiseState === MyPromise.PENDING) {this.fulfilledCallBacks.push(() => {setTimeout(() => {let x = onFulfilled(this.PromiseResult)
            x instanceof MyPromise ? x.then(resolve, reject) : resolve(x)
          })
        })
        this.rejectedCallBacks.push(() => {setTimeout(() => {let x = onRejected(this.PromiseResult)
            x instanceof MyPromise ? x.then(resolve, reject) : reject(x)
          })
        })
      } else if (this.PromiseState === MyPromise.FULFILLED) {
        try {setTimeout(() => {let x = onFulfilled(this.PromiseResult)
            x instanceof MyPromise ? x.then(resolve, reject) : resolve(x)
          })
        } catch (error) {reject(error)
        }
      } else {
        try {setTimeout(() => {let x = onRejected(this.PromiseResult)
            x instanceof MyPromise ? x.then(resolve, reject) : reject(x)
          })
        } catch (error) {reject(error)
        }
      }
    })
  }

  //value 要解析为 Promise 对象的值
  static resolve(value) {
    // 如果是
    if (value instanceof MyPromise) {return value} else if (value && typeof value === 'object' && 'then' in value) {return new MyPromise((resolve, reject) => {value.then(resolve, reject)
      })
    }
    return new MyPromise((resolve) => {resolve(value)
    })
  }
  static all(promiseList) {if (Array.isArray(promiseList)) {return new MyPromise((resolve, reject) => {if (promiseList.length === 0) {resolve(promiseList)
        }
        let count = 0
        let result = []
        promiseList.forEach((item, index) => {if (item instanceof MyPromise) {MyPromise.resolve(item).then((res) => {
                count++
                result[index] = res
                count === promiseList.length && resolve(result)
              },
              (error) => {reject(error)
              }
            )
          } else {
            count++
            result[index] = item
            count === promiseList.length && resolve(result)
          }
        })
      })
    } else {throw TypeError('argument must be Array')
    }
  }
}

// 捕捉异样

const promise1 = MyPromise.resolve(3)
const promise2 = 42
const promise3 = new MyPromise((resolve, reject) => {setTimeout(() => {resolve(100)
  })
})

MyPromise.all([promise1, promise2, promise3]).then((values) => {console.log(values)
})
// [3, 42, 100]

实现 Promise.allSettled

Promise.allSettled(iterable)办法返回一个在所有给定的 promise 都曾经 fulfilled 或 rejected 后的 promise,并带有一个对象数组,每个对象示意对应的 promise 后果。

  • 当你有多个彼此不依赖的异步工作胜利实现时,或者你总是想晓得每个 promise 的后果时,通常应用它。
  • 相比之下,Promise.all() 更适宜彼此相互依赖或者在其中任何一个 reject 时立刻完结。

参数 iterable 是一个可迭代的对象,例如 Array,其中每个成员都是 Promise。

对于每个后果对象,都有一个 status 字符串。如果它的值为 fulfilled,则后果对象上存在一个 value。如果值为 rejected,则存在一个 reason。value(或 reason)反映了每个 promise 决定(或回绝)的值。

举个🌰:

let p1=Promise.resolve(1)
let p2=Promise.reject(2)
let p3=Promise.resolve(3)
let p4=Promise.reject(4)
Promise.allSettled([p1,p2,p3,p4]).then(res=>{console.log(res)
})
    // 返回了一个数组
    [{status: 'fulfilled', value: 1},
{status: 'rejected', reason: 2},
{status: 'fulfilled', value: 3},
{status: 'rejected', reason: 4}]
 class MyPromise {
        static PENDING = 'pending'
        static FULFILLED = 'fulfilled'
        static REJECTED = 'rejected'
        constructor(executor) {
          this.PromiseState = MyPromise.PENDING
          this.PromiseResult = null
          this.fulfilledCallBacks = []
          this.rejectedCallBacks = []
          try {executor(this.resolve.bind(this), this.reject.bind(this))
          } catch (error) {this.reject(error)
          }
        }
        resolve(result) {if ((this.PromiseState = MyPromise.PENDING)) {setTimeout(() => {
              this.PromiseState = MyPromise.FULFILLED
              this.PromiseResult = result
              for (const callBack of this.fulfilledCallBacks) {callBack(result)
              }
            })
          }
        }
        reject(reason) {if ((this.PromiseState = MyPromise.PENDING)) {setTimeout(() => {
              this.PromiseState = MyPromise.REJECTED
              this.PromiseResult = reason
              for (const callBack of this.rejectedCallBacks) {callBack(reason)
              }
            })
          }
        }
        then(onFulfilled, onRejected) {
          onFulfilled =
            typeof onFulfilled === 'function' ? onFulfilled : (val) => val
          onRejected =
            typeof onRejected === 'function'
              ? onRejected
              : (err) => {throw err}
          return new MyPromise((resolve, reject) => {if (this.PromiseState === MyPromise.PENDING) {this.fulfilledCallBacks.push(() => {setTimeout(() => {let x = onFulfilled(this.PromiseResult)
                  x instanceof MyPromise ? x.then(resolve, reject) : resolve(x)
                })
              })
              this.rejectedCallBacks.push(() => {setTimeout(() => {let x = onRejected(this.PromiseResult)
                  x instanceof MyPromise ? x.then(resolve, reject) : reject(x)
                })
              })
            } else if (this.PromiseState === MyPromise.FULFILLED) {
              try {setTimeout(() => {let x = onFulfilled(this.PromiseResult)
                  x instanceof MyPromise ? x.then(resolve, reject) : resolve(x)
                })
              } catch (error) {reject(error)
              }
            } else {
              try {setTimeout(() => {let x = onRejected(this.PromiseResult)
                  x instanceof MyPromise ? x.then(resolve, reject) : reject(x)
                })
              } catch (error) {reject(error)
              }
            }
          })
        }

        //value 要解析为 Promise 对象的值
        static resolve(value) {
          // 如果是
          if (value instanceof MyPromise) {return value} else if (value && typeof value === 'object' && 'then' in value) {return new MyPromise((resolve, reject) => {value.then(resolve, reject)
            })
          }
          return new MyPromise((resolve) => {resolve(value)
          })
        }
        static allSettled(promiseList) {if (Array.isArray(promiseList)) {return new MyPromise((resolve, reject) => {
              let count = 0
              let result = []
              // 如果传入的是一个空数组,那么就间接返回一个 resolved 的空数组 promise 对象
              if (promiseList.length === 0) {return resolve(promiseList)
              }
              promiseList.forEach((item, index) => {MyPromise.resolve(item).then((res) => {
                      count++
                      result[index] = {
                        status: MyPromise.FULFILLED,
                        value: res,
                      }
                      count === promiseList.length && resolve(result)
                    },
                    (error) => {
                      count++
                      result[index] = {
                        status: MyPromise.REJECTED,
                        reason: error,
                      }
                      count === promiseList.length && resolve(result)
                    }
                  )
              })
            })
          } else {throw TypeError('argument must be Array')
          }
        }
      }

      // 测试代码

      const promise1 = MyPromise.resolve(3)
      const promise2 = 1
      const promises = [promise1, promise2]

      MyPromise.allSettled(promises).then((results) =>
        results.forEach((result) => console.log(result))
      )

      setTimeout(() => {const p1 = MyPromise.resolve(3)
        const p2 = new MyPromise((resolve, reject) =>
          setTimeout(reject, 100, 'foo')
        )
        const ps = [p1, p2]

        MyPromise.allSettled(ps).then((results) =>
          results.forEach((result) => console.log(result))
        )
      }, 1000)

      MyPromise.allSettled([]).then((results) => console.log(results))
// 打印后果
(0) []
{status: 'fulfilled', value: 3}
{status: 'fulfilled', value: 1}
{status: 'fulfilled', value: 3}
{status: 'rejected', reason: 'foo'}

\

实现 Promise.any

Promise.any() 接管一个 Promise 可迭代对象,只有其中的一个 promise 胜利,就返回那个曾经胜利的 promise。

如果可迭代对象中没有一个 promise 胜利(即所有的 promises 都失败 / 回绝),就返回一个失败的 promise 和 AggregateError 类型的实例,它是 Error 的一个子类,用于把繁多的谬误汇合在一起。

  • 如果传入的参数是一个空的可迭代对象,则返回一个 已失败(already rejected)状态的 Promise。
  • 如果传入的参数不蕴含任何 promise,则返回一个 异步实现(asynchronously resolved)的 Promise。(将非 Promise 值,转换为 Promise 并当做胜利)
  • 只有传入的迭代对象中的任何一个 promise 变成胜利(resolve)状态,或者其中的所有的 promises 都失败,那么返回的 promise 就会 异步地(当调用栈为空时)变成胜利 / 失败(resolved/reject)状态。(如果所有 Promise 都失败,则报错)
 class MyPromise {
        static PENDING = 'pending'
        static FULFILLED = 'fulfilled'
        static REJECTED = 'rejected'
        constructor(executor) {
          this.PromiseState = MyPromise.PENDING
          this.PromiseResult = null
          this.fulfilledCallBacks = []
          this.rejectedCallBacks = []
          try {executor(this.resolve.bind(this), this.reject.bind(this))
          } catch (error) {this.reject(error)
          }
        }
        resolve(result) {if ((this.PromiseState = MyPromise.PENDING)) {setTimeout(() => {
              this.PromiseState = MyPromise.FULFILLED
              this.PromiseResult = result
              for (const callBack of this.fulfilledCallBacks) {callBack(result)
              }
            })
          }
        }
        reject(reason) {if ((this.PromiseState = MyPromise.PENDING)) {setTimeout(() => {
              this.PromiseState = MyPromise.REJECTED
              this.PromiseResult = reason
              for (const callBack of this.rejectedCallBacks) {callBack(reason)
              }
            })
          }
        }
        then(onFulfilled, onRejected) {
          onFulfilled =
            typeof onFulfilled === 'function' ? onFulfilled : (val) => val
          onRejected =
            typeof onRejected === 'function'
              ? onRejected
              : (err) => {throw err}
          return new MyPromise((resolve, reject) => {if (this.PromiseState === MyPromise.PENDING) {this.fulfilledCallBacks.push(() => {setTimeout(() => {let x = onFulfilled(this.PromiseResult)
                  x instanceof MyPromise ? x.then(resolve, reject) : resolve(x)
                })
              })
              this.rejectedCallBacks.push(() => {setTimeout(() => {let x = onRejected(this.PromiseResult)
                  x instanceof MyPromise ? x.then(resolve, reject) : reject(x)
                })
              })
            } else if (this.PromiseState === MyPromise.FULFILLED) {
              try {setTimeout(() => {let x = onFulfilled(this.PromiseResult)
                  x instanceof MyPromise ? x.then(resolve, reject) : resolve(x)
                })
              } catch (error) {reject(error)
              }
            } else {
              try {setTimeout(() => {let x = onRejected(this.PromiseResult)
                  x instanceof MyPromise ? x.then(resolve, reject) : reject(x)
                })
              } catch (error) {reject(error)
              }
            }
          })
        }
        catch(onRejected) {return this.then(undefined, onRejected)
        }
        //value 要解析为 Promise 对象的值
        static resolve(value) {
          // 如果是
          if (value instanceof MyPromise) {return value} else if (value && typeof value === 'object' && 'then' in value) {return new MyPromise((resolve, reject) => {value.then(resolve, reject)
            })
          }
          return new MyPromise((resolve) => {resolve(value)
          })
        }
        static any(promiseList) {if (Array.isArray(promiseList)) {return new MyPromise((resolve, reject) => {
              let count = 0
              let errors = []
              // 留神留神:如果传入的参数是一个空的可迭代对象,则返回一个 已失败(already rejected)状态的 Promise。if (promiseList.length === 0) return reject(new AggregateError('All promises were rejected'));
              promiseList.forEach((item, index) => {MyPromise.resolve(item).then((res) => {resolve(res)
                  },
                  (reason) => {
                    count++
                    errors.push(reason)
                    /**+                            * 如果可迭代对象中没有一个 promise 胜利,就返回一个失败的 promise 和 AggregateError 类型的实例,+                            * AggregateError 是 Error 的一个子类,用于把繁多的谬误汇合在一起。+                            */
                    count === promiseList.length &&
                      reject(new AggregateError(errors))
                  }
                )
              })
            })
          } else {throw TypeError('argument must be Array')
          }
        }
      }

      // 测试代码

      MyPromise.any([]).catch((e) => {console.log(e)
      })

      const pErr = new Promise((resolve, reject) => {reject('总是失败')
      })

      const pSlow = new Promise((resolve, reject) => {setTimeout(resolve, 500, '最终实现')
      })

      const pFast = new Promise((resolve, reject) => {setTimeout(resolve, 100, '很快实现')
      })

      Promise.any([pErr, pSlow, pFast]).then((value) => {console.log(value)
        // 冀望输入: "很快实现"
      })

      const pErr1 = new MyPromise((resolve, reject) => {reject('总是失败')
      })

      const pErr2 = new MyPromise((resolve, reject) => {reject('总是失败')
      })

      const pErr3 = new MyPromise((resolve, reject) => {reject('总是失败')
      })

      MyPromise.any([pErr1, pErr2, pErr3]).catch((e) => {console.log(e)
      })
      // 打印后果
//       AggregateError: All promises were rejected
// AggregateError: All promises were rejected
// 很快实现

实现 race 办法

Promise.race(iterable) 办法返回一个 promise,一旦迭代器中的某个 promise 解决或回绝,返回的 promise 就会解决或回绝。

一个待定的 Promise 只有给定的迭代中的一个 promise 解决或回绝,就采纳第一个 promise 的值作为它的返回值,从而异步地解析或回绝(一旦堆栈为空)。

race 函数返回一个 Promise,它将与第一个传递的 promise 雷同的实现形式被实现。它能够是实现(resolves),也能够是失败(rejects),这要取决于第一个实现的形式是两个中的哪个。

  • 如果传的迭代是空的,则返回的 promise 将永远期待。
  • 如果迭代蕴含一个或多个非承诺值和 / 或已解决 / 回绝的承诺,则 Promise.race 将解析为迭代中找到的第一个值。
  class MyPromise {
        static PENDING = 'pending'
        static FULFILLED = 'fulfilled'
        static REJECTED = 'rejected'
        constructor(executor) {
          this.PromiseState = MyPromise.PENDING
          this.PromiseResult = null
          this.fulfilledCallBacks = []
          this.rejectedCallBacks = []
          try {executor(this.resolve.bind(this), this.reject.bind(this))
          } catch (error) {this.reject(error)
          }
        }
        resolve(result) {if ((this.PromiseState = MyPromise.PENDING)) {setTimeout(() => {
              this.PromiseState = MyPromise.FULFILLED
              this.PromiseResult = result
              for (const callBack of this.fulfilledCallBacks) {callBack(result)
              }
            })
          }
        }
        reject(reason) {if ((this.PromiseState = MyPromise.PENDING)) {setTimeout(() => {
              this.PromiseState = MyPromise.REJECTED
              this.PromiseResult = reason
              for (const callBack of this.rejectedCallBacks) {callBack(reason)
              }
            })
          }
        }
        then(onFulfilled, onRejected) {
          onFulfilled =
            typeof onFulfilled === 'function' ? onFulfilled : (val) => val
          onRejected =
            typeof onRejected === 'function'
              ? onRejected
              : (err) => {throw err}
          return new MyPromise((resolve, reject) => {if (this.PromiseState === MyPromise.PENDING) {this.fulfilledCallBacks.push(() => {setTimeout(() => {let x = onFulfilled(this.PromiseResult)
                  x instanceof MyPromise ? x.then(resolve, reject) : resolve(x)
                })
              })
              this.rejectedCallBacks.push(() => {setTimeout(() => {let x = onRejected(this.PromiseResult)
                  x instanceof MyPromise ? x.then(resolve, reject) : reject(x)
                })
              })
            } else if (this.PromiseState === MyPromise.FULFILLED) {
              try {setTimeout(() => {let x = onFulfilled(this.PromiseResult)
                  x instanceof MyPromise ? x.then(resolve, reject) : resolve(x)
                })
              } catch (error) {reject(error)
              }
            } else {
              try {setTimeout(() => {let x = onRejected(this.PromiseResult)
                  x instanceof MyPromise ? x.then(resolve, reject) : reject(x)
                })
              } catch (error) {reject(error)
              }
            }
          })
        }
        catch(onRejected) {return this.then(undefined, onRejected)
        }
        //value 要解析为 Promise 对象的值
        static resolve(value) {
          // 如果是
          if (value instanceof MyPromise) {return value} else if (value && typeof value === 'object' && 'then' in value) {return new MyPromise((resolve, reject) => {value.then(resolve, reject)
            })
          }
          return new MyPromise((resolve) => {resolve(value)
          })
        }
        static race(promiseList) {if (Array.isArray(promiseList)) {return new MyPromise((resolve, reject) => {
              // 留神留神:如果传入的参数是一个空的可迭代对象,则永远为 pending 状态
              if (promiseList.length > 0) {promiseList.forEach((item, index) => {
                  /**                   * 如果迭代蕴含一个或多个非承诺值和 / 或已解决 / 回绝的承诺,* 则 Promise.race 将解析为迭代中找到的第一个值。*/
                  MyPromise.resolve(item).then(resolve, reject)
                })
              }
            })
          } else {throw TypeError('argument must be Array')
          }
        }
      }

      // 测试代码

      /**       * 验证 Promise.race()办法       */

      // 数组全是非 Promise 值,测试通过
      let p1 = Promise.race([1, 3, 4])
      setTimeout(() => {console.log('p1 :>>', p1) //1
      })

      // 空数组,测试通过
      let p2 = Promise.race([])
      setTimeout(() => {console.log('p2 :>>', p2) //pengding
      })

      //  p1 :>>  Promise {<fulfilled>: 1}
      //   p2 :>>  Promise {<pending>}

总结:

Promise 办法 总结 传递 [] 数组影响
all() 参数所有后果为胜利才执行 then 办法返回后果,否则 catch 办法为第一个 rejected 的 Promise 返回一个已实现(already resolved)状态的 Promise(resolve([]))
allSettled() 不论 Promise 的后果是否胜利,都要等后果返回结束之后执行 then 办法
race() 只有有一个 Promise 有了后果,就决定了最终新 Promise 的状态 始终处于 pending 状态
any() 只有有一个 Promise 为胜利,就会这个胜利 Promise 的后果,如果所有 Promise 为失败,那么最终新 Promise 的状态为 rejected 且报错 Promise 的状态为 rejected 且报错(AggregateError)
finally() 不论 Promise 对象无论变成 fulfilled 还是 reject 状态,最终都会被执行的代码
退出移动版