Loading... #### 前言 Promise的then方法如果返回一个数值,会在链式then的下一次回调中打印出来,除此之外,如果then方法返回一个promise则会在下一个then中返回上一个返回的promise的执行结果,这次慢慢来实现,符合promiseA+规范的 ``` const PENDING = 'PENDING' const FULFILLED = 'FULFILLED' const REJECTED = 'REJECTED' function resolvePromise(x, promise2, resolve, reject) { //判断如果x和promise2相等则抛出异常 if (x === promise2) { return reject(new TypeError('类型错误')) } //判断一下返回的是不是对象或者函数 if ((typeof x === 'object' && x !== null) || typeof x === 'function') { let called try { let then = x.then if (typeof then === 'function') { then.call(x, function (y) { if (called) return //递归解析 直到是一个普通值为止 resolvePromise(y, promise2, resolve, reject) }, function (reason) { if (called) return reject(reason) }) } else { //是个普通对象 resolve(x) } } catch (error) { if (called) return resolve(error) } } else { //如果不是则代表是普通数值 resolve(x) } } class Promise { constructor(executor) { this.value = '' this.reason = '' this.status = PENDING this.onFulfilledCBArr = [] this.onRejectedCBArr = [] executor(resolve.bind(this), reject.bind(this)) function resolve(params) { this.status = FULFILLED this.value = params this.onFulfilledCBArr.forEach(fn => fn()) } function reject(params) { this.status = REJECTED this.reason = params this.onRejectedCBArr.forEach(fn => fn()) } } then(onFulfilledCB, onRejectedCB) { //如果不传则放过去 onFulfilledCB = typeof onFulfilledCB === 'function' ? onFulfilledCB : x => x onRejectedCB = typeof onRejectedCB === 'function' ? onFulfilledCB : err => { throw err } let promise2 = new Promise((resolve, reject) => { if (this.status === FULFILLED) { try { setTimeout(() => { let x = onFulfilledCB(this.value) resolvePromise(x, promise2, resolve, reject) }, 0); } catch (error) { reject(error) } } if (this.status === REJECTED) { try { setTimeout(() => { let x = onRejectedCB(this.reason) resolvePromise(x, promise2, resolve, reject) }, 0); } catch (error) { reject(error) } } if (this.status === PENDING) { this.onFulfilledCBArr.push(() => { try { let x = onFulfilledCB(this.value) resolve(x) } catch (error) { reject(error) } }) this.onRejectedCBArr.push(() => { try { let x = onRejectedCB(this.reason) resolve(x) } catch (error) { reject(error) } }) } }) return promise2 } } module.exports = Promise ``` Last modification:December 6th, 2020 at 11:47 pm © 允许规范转载 Support If you think my article is useful to you, please feel free to appreciate ×Close Appreciate the author Sweeping payments Pay by AliPay Pay by WeChat