2021年2月4日星期四

手写Promise实现过程

手写Promise实现过程

  • 1、实现Promise的核心功能
  • 2、判断下当执行器里面时异步代码时的回调函数调用情况
  • 3、then方法多次调用的情况
  • 4、then方法的链式调用,以及如何把then方法的返回值传递到下一个then方法中,再判断返回值是普通值还是peomise对象进而进一步处理
  • 5、判断then方法返回的对象是否和该then方法的promise对象是否相同
  • 6、捕获错误:执行器中捕获,成功、失败、等待下回调函数中捕获错误
  • 7、then方法的参数变成可传参数
  • 8、Prmomise.all()方法
  • 9、Prmomise.resolve() 方法
  • 10、finally方法
  • 11、catch方法
 // 定义好MyPromise的三种状态,用三个常量来接收  const PENDING = 'pending' // 等待  const FULFILLED = 'fulfilled' // 成功  const REJECTED = 'rejected' // 失败 class MyPromise { // MyPromise接收一个参数,这个参数是构造器函数,并且在创建MyPromise的实例对象时,这个构造器函数会立即执行 constructor(executor) {  // 构造器函数接受两个参数:resolve、reject这两个方法  // 捕获执行器错误  try {  executor(this.resolve, this.reject)  } catch (e) {  this.reject(e)  } } // MyPromise 有三种状态 分别是:pending、fulfilled、rejected,一开始是pending状态 status = PENDING value = undefined // resolve传递的值 reason = undefined// reject传递的错误信息 // successCallBack = undefined  successCallBack = [] // then方法多次调用时且执行器里面是异步时需将then方法里面的回调函数依此存储在该数组中 // failCallBack = undefined failCallBack = [] // 同上 resolve = (val) => {  if (this.status !== PENDING) return // 如果不是pending 状态则阻止往下执行,因为状态一旦改变,便不可更改  // 执行resolve方法时 状态status修改为fulfilled  this.status = FULFILLED  // 将成功调用传递的值传给this.value保存起来方便后续使用  this.value = val  // 判断下this.successCallBack是否存在,如果存在则调用  // this.successCallBack && this.successCallBack(this.value)  // 从this.successCallBack中一个个取出成功回调函数调用并从数组中删除  // for (let i = this.successCallBack.length; i > 0; i--) {  // // this.successCallBack.shift()(this.value)  // this.successCallBack.shift()()  // }  while(this.successCallBack.length) this.successCallBack.shift()() } reject = (reason) => {  if (this.status !== PENDING) return  // 执行resolve方法时 状态status修改为rejected  this.status = REJECTED  // 将成功调用传递的值传给this.value保存起来方便后续使用  this.reason = reason  // 同理,同上  // this.failCallBack && this.failCallBack(this.reason)  // 同上  // for (let i = this.failCallBack.length; i > 0; i--) {  // // this.failCallBack.shift()(this.reason)  // this.failCallBack.shift()()  // }  while(this.failCallBack.length) this.failCallBack.shift()() } then(successCallBack, failCallBack) {  /****then方法不传递回调函数时 */  successCallBack = successCallBack ? successCallBack : value => value  failCallBack = failCallBack ? failCallBack : reason => { throw reason }  /***then方法实现链式调用 */  // 能够让then方法实现链式调用,说明then方法返回的还是一个 Promise对象,我们现在就再创建个 Promise对象 promise2,并将其返回  let promise2 = new MyPromise((resolve, reject) => {  /**** then方法里面的回调函数仍需要立即执行,所以我们将他们放在 promise2的执行器函数中*/  // 根据status的状态判断该调用哪个回调函数,fulfilled则调用成功回调函数,rejected则调用failCallBack回调函数  if (this.status === FULFILLED) {   // then方法返回的 promise2需要执行 resolve 方法将当前 then方法回调函数的返回值传递给下一个then方法的回调函数中   setTimeout(() => {   // 捕获回调函数错误   try {    let x = successCallBack(this.value)    // 需要判断下 x 是普通值还是promise对象,    // 如果是普通值直接调用resolve方法,    // 如果是 Promise对象则需要查看promise对象返回的结果    // 再根据promise对象返回的结果,决定调用resolve 还是reject    // 此时还获取不到promise2, 因为promise2需要等到new MyPromise执行完毕之后才会获取到,需加个异步代码    newPromise(promise2, x, resolve, reject) // 将then方法返回的promise对象promise2也传递过去用于判断 then方法return的x是否相同   } catch(e) {    reject(e)   }   }, 0);   // resolve(x)   // 调用成功回调函数,并传递成功时的值   //successCallBack(this.value) // then方法被多次调用时,同步情况无需处理,直接调用即可  } else if(this.status === REJECTED) {   // 调用失败回调函数,并传递失败的原因   //failCallBack(this.reason)  // 同上   setTimeout(() => {   try {    let x = failCallBack(this.reason)    newPromise(promise2, x, resolve, reject)   } catch(e) {    reject(e)   }   }, 0);  } else { // 当执行器中时异步代码时并没有立即调用resolve 或reject,所以status状态既不是fulfilled也不是 rejected,而是还处于pending状态     // this.successCallBack = successCallBack   // 此时将then的回调函数存起来当status状态改变后再去调用回调函数   // this.successCallBack.push(successCallBack)   // 捕获错误   this.successCallBack.push(() =>{   setTimeout(() => {    try {    let x = successCallBack(this.value)    newPromise(promise2, x, resolve, reject)    } catch(e) {    reject(e)    }   }, 0);   })   // this.failCallBack = failCallBack   // this.failCallBack.push(failCallBack)   this.failCallBack.push(() => {   setTimeout(() => {    try {    let x = failCallBack(this.reason)    newPromise(promise2, x, resolve, reject)    } catch(e) {    reject(e)    }   }, 0);   })  }  })  return promise2; } /***finally 无论该Promise对象是成功还是失败都会执行 接受一个回调函数作为参数 */ finally(callBack) {  // finally最终返回Promise对象,而then方法返回的就时Promise对象  return this.then(value => {  return MyPromise.resolve(callBack()).then(() => value);  }, reason => {  return MyPromise.resolve(callBack()).then(() => { throw reason })  }) } /****catch方法 */ catch (failCallBack) {  return this.then(undefined, failCallBack) } // 静态方法all,接受参数是一个数组 static all(arr) {  // all方法的then方法的回调返回值是一个数组,定义一个数组来接收  let result = []  let index = 0  // 返回值是一个peomise对象  return new MyPromise((resolve, reject) => {  function addData(k, v) {   result[k] = v   index++   if (index === result.length) {   resolve(result)   }  }  for(let i=0; i<arr.length; i++) {   let current = arr[i]   if(current instanceof MyPromise) {   current.then(res => {    addData(i, res)   }, reason => reject(reason))   } else {   addData(i, arr[i])   }  }  }) } /** 静态方法 resolve,返回值是一个Promise对象,接受一个参数,当这个参数是Promise对象时  * 就将该对象作为 resolve方法的返回值,如果是个普通值,则将该值包裹在一个Promise对象中作为  * resolve方法的返回值  */ static resolve(value) {  if (value instanceof MyPromise) return value  return new MyPromise((resolve) => resolve(value))  } } function newPromise(promise2, x, resolve, reject) {  if (promise2 === x) {  return reject(new TypeError('循环返回相同的peomise对象')) //加return 阻止代码往下进行  }  if (x instanceof MyPromise) {  x.then(resolve, reject)  } else {  resolve(x) } }








原文转载:http://www.shaoqun.com/a/525603.html

跨境电商:https://www.ikjzd.com/

雨果:https://www.ikjzd.com/w/1307

凹凸曼:https://www.ikjzd.com/w/1392


手写Promise实现过程1、实现Promise的核心功能2、判断下当执行器里面时异步代码时的回调函数调用情况3、then方法多次调用的情况4、then方法的链式调用,以及如何把then方法的返回值传递到下一个then方法中,再判断返回值是普通值还是peomise对象进而进一步处理5、判断then方法返回的对象是否和该then方法的promise对象是否相同6、捕获错误:执行器中捕获,成功、失败、
mail.ru:mail.ru
华翰物流:华翰物流
选品:疫情之下,这四种美容产品成为消费者新宠:选品:疫情之下,这四种美容产品成为消费者新宠
亚马逊欧洲站即将推出计划政策变更:亚马逊欧洲站即将推出计划政策变更
受疫情影响 Shopee调整多项政策:受疫情影响 Shopee调整多项政策

没有评论:

发表评论

注意:只有此博客的成员才能发布评论。