PromiseA+规范之手写Promise
前言
1、Promise 的意义?
在javascript的世界中,所有代码都是单线程执行的,由于这个“缺陷”,导致JavaScript的所有网络操作,浏览器事件,都必须是异步执行。Ajax可以解决这个问题,但是并不好复用。JQuery的链式调用同样可以解决,每次调用都会返回一个JQuery对象。为了更好的处理Promise 出现了,并且ECMAScript 对其进行了规范。
2、PromiseA+规范是什么?
其实
Promise
规范有很多,如Promise/A
,Promise/B
,Promise/D
以及Promise/A
的升级版Promise/A+
。ES6 (也叫ES2015)中采用了Promise/A+
规范。
目录
一、术语
二、Promise Status(三种状态及其关系)
1. pending
2. fulfilled
3. rejected
总结:
三、Promise then 方法 及其返回值
四、规范
1.参数的规范
2. onFulfilled 特性
3. onRejected 特性
4. onFulfilled 和 onRejected 应该是在微任务阶段执行
5. then方法可以被调用多次
6. 返回值
7. resolvePromise
五、实现promise的具体步骤(大概九步);
1. promise 应该是一个构造函数或者 class
2.定义三种状态
3.初始化状态
4.实现 resolve 和 reject
5.对于实例化 promise 时的入参处理
6.实现 then 方法
7. then 的返回值
8. resolvePromise 方法的具体实现
9. onFulfilled 和 onRejected 是在微任务中执行的
到这里我们 简单的 promise 已经实现了,可以简单的去测试一下
一、术语
1. promise 有 then 方法的对象或者函数;
2. thenable 是一个有 then 方法的对象或者是函数;
3. value promise 状态成功时的值, resolve(value),可以是任何数据类型(String Number Boolean undefined thenable promise);
4. reason promise 状态失败时的值, reject(reason);
二、Promise Status(三种状态及其关系)
1. pending
1.1 初始状态,可以改变.
1.2 在 resolve 和 reject 之前都处于这个状态.
1.3 通过resolve --> fulfilled 状态.
1.4 通过reject --> rejected 状态.
2. fulfilled
2.1 最终态,不可改变.
2.2 一个 promise 被 resolve 改变成这个状态.
2.3 必须通过一个 value 值,成功以后的值.
3. rejected
3.1 最终态,不可改变;
3.2 一个promise 被 reject 改变成这个状态;
3.3 必须拥有一个 reason ,也就是失败的原因;
总结:
pending --> resolve(value) --> fulfilled
pending --> reject(reason) --> rejected
三、Promise then 方法 及其返回值
promise 应该(promiseA+规范,规范提出了,所以用的应该)提供一个 then 方法, 用来访问最终结果, 无论 value 还是 reason.
promise.then(onFuilled,onRejected)
四、规范
1.参数的规范
1.1 onFulfilled 必须是函数类型, 如果不是函数类型 ,应该被忽略(这里的忽略是指给一个默认值,并不是真正意义上的忽略);
1.2 onRejected 必须是函数类型, 如果不是函数类型 ,应该被忽略(同上);
2. onFulfilled 特性
2.1 在 promise 变成 fulfilled 时, 应该调用 onFulfilled ,参数是 value;(onFulfilled 的执行时机?)
2.2 在 promise 变成 fulfilled 之前, 不应该调用 onFulfilled;
2.3 只能被调用一次,可以注册若干个回调函数(promise.then().then().then()....);(怎么实现只调用一次?)
3. onRejected 特性
3.1 在 promise 变成 rejected 时, 调用 onRejected ,参数是reason;
3.2 在 promise 变成 rejected 之前,不应该调用 onRejected.
3.3 只能调用一次
4. onFulfilled 和 onRejected 应该是在微任务阶段执行
为什么微任务阶段执行?
一定要等前面的任务执行完,才进行调用. 微任务是在一轮宏任务执行完之后执行;
5. then方法可以被调用多次
5.1 promise 变成 fulfilled 之后 , 所有的 onFulfilled 回调都应该按照注册的顺序执行,也可以理解为按照 .then() 的顺序执行;
例:
promise.then(onFulfilled , onRejected).then(onFulfilled1 => ( )).then(....)
5.2 promise 变成 rejected 之后 , 所有的 onRejected 回调都应该按照注册的顺序执行,也可以理解为按照 .then() 的顺序执行;
6. 返回值
规范里定义 then 应该返回一个promise
const promise2 = promise( onFulfilled , onRejected );
6.1 onFulfilled 或 onRejected 执行结果 为 x(任何东西:值或者 promise),调用resolvePromise;
6.2 onFulfilled 或 onRejected 执行过程中抛出了异常,promise2需要被 reject;
6.3 如果 onFulfilled 不是一个函数,promise2 应该以 promise1 的value 触发 fulfilled;
6.4. 如果 onRejected 不是一个函数,promise2 应该以 promise1 的reason 触发 fulfilled
7. resolvePromise
promise2:当前第一个promise 的返回值;
X:无论是 onFulfilled 还是 onRejected 的执行结果
resolve、reject :变更方法
resolvePromise(promise2, x, resolve, reject)
7.1 如果promise2 和 x 相等 reject typeError;
7.2 如果 x 是一个 promise
如果 x 是pending 状态 ,promise 必须要在pending 状态,直到 x 的状态变更。
如果 x 是 fulfilled ,value --> fulfilled
如果 x 是 rejected ,reason --> rejected
7.3 如果 x 是一个 Object 或者 Function
去获取 x.then(),如果报错,reject reason
如果 then 是一个函数,then.call(x, resolvePromiseFn, rejectPromiseFn)
为什么用 call 改变 this 指针,或者then的时候可能会导致 指针指向改变,所以用 call 继续执行之前的逻辑
五、实现promise的具体步骤(大概九步);
1. promise 应该是一个构造函数或者 class
const promise = new promise();
新建promise-class.js,今天我们用class 来实现promise
class MPromise{constructor(){}
}
2.定义三种状态
const PENDING = 'pending';
const FULFILLED = 'fulfilled';
const REJECTED = 'rejected';class MPromise{constructor(){}
}
3.初始化状态
const PENDING = 'pending';
const FULFILLED = 'fulfilled';
const REJECTED = 'rejected';class MPromise{constructor(){this.status = PENDING;this.value = null;this.reason = null;}
}
4.实现 resolve 和 reject
4.1 这两个方法要更改 status,从 pending 变成 fulfilled / rejected
4.2 入参分别是 value 和 reason
const PENDING = 'pending';
const FULFILLED = 'fulfilled';
const REJECTED = 'rejected';class MPromise{constructor(){this.status = PENDING;this.value = null;this.reason = null;}resolve(value){// 最终态不可被改变,所以需要加一个判断// 只有当 status 为初始态的时候才可以改变if(this.status === PENDING){this.status = FULFILLED;this.value = value;}}reject(reason){if(this.status === PENDING){this.status = REJECTED;this.reason= reason;}}
}
5.对于实例化 promise 时的入参处理
5.1 入参是一个函数
const promise = new promise((resolve,reject)=>{})
5.2 接受 resolve 和 rejected 两个参数
5.3 初始化 promise 就要同步执行这个函数,并且有任何报错都要通过 reject 抛出
const promise = new promise((resolve,reject)=>{axios.get('www.baidu.com')
}).then(result=>{// 这里需要注意一下,创建之处就已经执行了// 并不是调用 .then() 的时候才会执行// 同步执行的,所以可以缓存一个 promise ,需要用到的时候直接取值即可// 获取的时候 并不会再次发送请求,所以不用担心流量的偷跑 与 性能的问题})
const PENDING = 'pending';
const FULFILLED = 'fulfilled';
const REJECTED = 'rejected';class MPromise{constructor(fn){this.status = PENDING;this.value = null;this.reason = null;//需要里面调用,有报错需要立马抛出try{// 考虑严谨性,更改 this 指向为当前环境fn(this.resolve.bind(this), this.reject.bind(this));} catch(e){this.reject(e)}}resolve(value){// 最终态不可被改变,所以需要加一个判断// 只有当 status 为初始态的时候才可以改变if(this.status === PENDING){this.status = FULFILLED;this.value = value;}}reject(reason){if(this.status === PENDING){this.status = REJECTED;this.reason= reason;}}
}
6.实现 then 方法
6.1 then 接受 两个参数 onFulfilled 和 onRejected
6.2 检查并处理参数,如果参数不是一个 function 就忽略
6.3 需要根据当前 promise 的状态,调用不同的函数
如果 promise 是 fulfilled 的时候 我们需要调用 onFulfilled
如果 promise 是 rejected 的时候 我们需要调用 onRejected
6.4 首先拿到所有的回调,因为状态发生变化的时候,无论是成功还是失败我们都需要去执行对应的 回调;新建两个数组 ,分别存储成功和失败的回调,调用 then 的时候,如果还是pending 状态就存入数组。
6.5 在 status 发生变化的时候,执行对应的回调。这里用 es6 的 getter setter,监听 status 的变化,在发生变化的时候来做对应的操作;
这里说一下如果是ES5没有 getter setter,那么我们可以直接在resolve 和 reject 两个方法里面去更改 status 的状态;使用getter setter 后面可以更好的维护,不用关注 status ;
const PENDING = 'pending';
const FULFILLED = 'fulfilled';
const REJECTED = 'rejected';class MPromise{//直接生命两个数组即可,这里的数组不会被修改 只会被push进来// 状态完成的 listFULFILLED_CALLBACK_LIST = [];// 状态失败的 listREJECTED_CALLBACK_LIST = [];// 存储初始化 status _status = PENDING;constructor(fn){this.status = PENDING;this.value = null;this.reason = null;//需要里面调用,有报错需要立马抛出try{// 考虑严谨性,更改 this 指向为当前环境fn(this.resolve.bind(this), this.reject.bind(this));} catch(e){this.reject(e)}}get status(){// 所有真实的 status return this._status;}set status(newStatus){this._status = newStatus;// 判断不同的状态 执行不同的逻辑switch(newStatus){case FULFILLED: {// then 方法已经判断过是不是function 所以这里不需要判断// 在 status 发生变化的时候,执行对应的回调。this.FULFILLED_CALLBACK_LIST.forEach(callback=>{callback(this.value)});break;}case REJECTED: {this.REJECTED_CALLBACK_LIST.forEach(callback=>{callback(this.reason)});break;}}}resolve(value){// 最终态不可被改变,所以需要加一个判断// 只有当 status 为初始态的时候才可以改变if(this.status === PENDING){this.value = value;this.status = FULFILLED;}}reject(reason){if(this.status === PENDING){this.reason= reason;this.status = REJECTED;}}then(onFulfilled, onRejected){const fulFilledFn = this.isFunction(onFulfilled) ? onFulfilled : (value) => valueconst rejectedFn = this.isFunction(onRejected) ? onRejected : (reason) => throw(reason)switch(this.status){case FULFILLED: {fulFilledFn(this.value);break;}case REJECTED: {rejectedFn(this.reason);break;}case PENDING: {this.FULFILLED_CALLBACK_LIST.push(fulFilledFn);this.REJECTED_CALLBACK_LIST.push(rejectedFn);break;}}}isFunction(param){return typeof param === 'function';}
}
7. then 的返回值
7.1 如果 onFulfilled 或者 onRejected 抛出一个异常 e ,那么新的 promise 必须 reject e;
7.2 返回值应该是一个 promise
7.3 如果 onFulfilled 不是函数,且 promise1 成功(resolve 状态)执行,promise2 必须返回同样的状态和value;(规范里定义的)
7.4 如果 onRejected 不是函数,且 promise1 拒绝执行,promise2 必须返回同样的状态和 reason;
7.5 如果 onFulfilled 或者 onRejected 返回一个值 x ,运行 resolvePromise 方法。
const PENDING = 'pending';
const FULFILLED = 'fulfilled';
const REJECTED = 'rejected';class MPromise{//直接生命两个数组即可,这里的数组不会被修改 只会被push进来// 状态完成的 listFULFILLED_CALLBACK_LIST = [];// 状态失败的 listREJECTED_CALLBACK_LIST = [];// 存储初始化 status _status = PENDING;constructor(fn){this.status = PENDING;this.value = null;this.reason = null;//需要里面调用,有报错需要立马抛出try{// 考虑严谨性,更改 this 指向为当前环境fn(this.resolve.bind(this), this.reject.bind(this));} catch(e){this.reject(e)}}get status(){// 所有真实的 status return this._status;}set status(newStatus){this._status = newStatus;// 判断不同的状态 执行不同的逻辑switch(newStatus){case FULFILLED: {// then 方法已经判断过是不是function 所以这里不需要判断// 在 status 发生变化的时候,执行对应的回调。this.FULFILLED_CALLBACK_LIST.forEach(callback=>{callback(this.value)});break;}case REJECTED: {this.REJECTED_CALLBACK_LIST.forEach(callback=>{callback(this.reason)});break;}}}resolve(value){// 最终态不可被改变,所以需要加一个判断// 只有当 status 为初始态的时候才可以改变if(this.status === PENDING){this.value = value;this.status = FULFILLED;}}reject(reason){if(this.status === PENDING){this.reason= reason;this.status = REJECTED;}}then(onFulfilled, onRejected){const fulFilledFn = this.isFunction(onFulfilled) ? onFulfilled : (value) => valueconst rejectedFn = this.isFunction(onRejected) ? onRejected : (reason) => throw(reason)//如果 onFulfilled 或者 onRejected 抛出一个异常 e ,那么新的 promise 必须 reject e;const fulFilledFnWitchCatch = (resolve, reject, newPromise) => {try{// 不是一个函数 就直接resolve ,因为有返回值了,所以需要判断if(!this.isFunction(onFulfilled)){resolve(this.value)}else{const x = fulFilledFn(this.value);this.resolvePromise(newPromise, x, resolve, reject);}}catch(e) {reject(e)}}const rejectedFnWitchCatch = (resolve, reject, newPromise) => {try{if(!this.isFunction(onRejected)){reject(this.reason);}else{const x = rejectedFn(this.reason);this.resolvePromise(newPromise, x, resolve, reject); }}catch(e) {reject(e)}}switch(this.status){// then 的返回值是一个promisecase FULFILLED: {const newPromise = new MPromise((resolve, reject) => fulFilledFnWitchCatch(resolve, reject, newPromise));return newPromise;}case REJECTED: {const newPromise = new MPromise((resolve, reject) => rejectedFnWitchCatch(resolve, reject, newPromise));return newPromise;}case PENDING: {const newPromise = new MPromise((resolve, reject) => {this.FULFILLED_CALLBACK_LIST.push(() => fulFilledFnWitchCatch(resolve, reject, newPromise));this.REJECTED_CALLBACK_LIST.push(() => rejectedFnWitchCatch(resolve, reject, newPromise)); });return newPromise;}}}// 规范里定义resolvePromise 需要接受一个 newPromise// resolvePromise 函数的意义,就是对promise 各种值的处理// 让 promise 可以返回一个结果,无论是 resolve 还是 rejectresolvePromise(newPromise, x, resolve, reject){}isFunction(param){return typeof param === 'function';}
}
8. resolvePromise 方法的具体实现
resolvePromise 函数的意义,就是对promise 各种值的处理, 让 promise 可以返回一个结果,无论是 resolve 还是 reject
8.1 如果 promise2 和 x 相等
8.1 如果 x 是一个promise ,promise 必须要在 pending 状态,直到 x 的状态变更
如果 x fulfilled ,value ---> fulfilled
如果 x rejected ,reason ----> rejected
8.1 如果 x 是一个 object / Function
去获取 const then = x.then, reject reason
then 是一个函数,then.call(x,resolvePromiseFn, rejectPromiseFn)
const PENDING = 'pending';
const FULFILLED = 'fulfilled';
const REJECTED = 'rejected';class MPromise{//直接生命两个数组即可,这里的数组不会被修改 只会被push进来// 状态完成的 listFULFILLED_CALLBACK_LIST = [];// 状态失败的 listREJECTED_CALLBACK_LIST = [];// 存储初始化 status _status = PENDING;constructor(fn){this.status = PENDING;this.value = null;this.reason = null;//需要里面调用,有报错需要立马抛出try{// 考虑严谨性,更改 this 指向为当前环境fn(this.resolve.bind(this), this.reject.bind(this));} catch(e){this.reject(e)}}get status(){// 所有真实的 status return this._status;}set status(newStatus){this._status = newStatus;// 判断不同的状态 执行不同的逻辑switch(newStatus){case FULFILLED: {// then 方法已经判断过是不是function 所以这里不需要判断// 在 status 发生变化的时候,执行对应的回调。this.FULFILLED_CALLBACK_LIST.forEach(callback=>{callback(this.value)});break;}case REJECTED: {this.REJECTED_CALLBACK_LIST.forEach(callback=>{callback(this.reason)});break;}}}resolve(value){// 最终态不可被改变,所以需要加一个判断// 只有当 status 为初始态的时候才可以改变if(this.status === PENDING){this.value = value;this.status = FULFILLED;}}reject(reason){if(this.status === PENDING){this.reason= reason;this.status = REJECTED;}}then(onFulfilled, onRejected){const fulFilledFn = this.isFunction(onFulfilled) ? onFulfilled : (value) => valueconst rejectedFn = this.isFunction(onRejected) ? onRejected : (reason) => throw(reason)//如果 onFulfilled 或者 onRejected 抛出一个异常 e ,那么新的 promise 必须 reject e;const fulFilledFnWitchCatch = (resolve, reject, newPromise) => {try{// 不是一个函数 就直接resolve ,因为有返回值了,所以需要判断if(!this.isFunction(onFulfilled)){resolve(this.value)}else{const x = fulFilledFn(this.value);this.resolvePromise(newPromise, x, resolve, reject);}}catch(e) {reject(e)}}const rejectedFnWitchCatch = (resolve, reject, newPromise) => {try{if(!this.isFunction(onRejected)){reject(this.reason);}else{const x = rejectedFn(this.reason);this.resolvePromise(newPromise, x, resolve, reject); }}catch(e) {reject(e)}}switch(this.status){// then 的返回值是一个promisecase FULFILLED: {const newPromise = new MPromise((resolve, reject) => fulFilledFnWitchCatch(resolve, reject, newPromise));return newPromise;}case REJECTED: {const newPromise = new MPromise((resolve, reject) => rejectedFnWitchCatch(resolve, reject, newPromise));return newPromise;}case PENDING: {const newPromise = new MPromise((resolve, reject) => {this.FULFILLED_CALLBACK_LIST.push(() => fulFilledFnWitchCatch(resolve, reject, newPromise));this.REJECTED_CALLBACK_LIST.push(() => rejectedFnWitchCatch(resolve, reject, newPromise)); });return newPromise;}}}// 规范里定义resolvePromise 需要接受一个 newPromise// resolvePromise 函数的意义,就是对promise 各种值的处理// 让 promise 可以返回一个结果,无论是 resolve 还是 rejectresolvePromise(newPromise, x, resolve, reject){if(newPromise === x){// 返回一个错误信息,信息无所谓什么都可以// 为什么要 reject 一个错误信息,因为如果 newPromise 和 x 相等会相互调用,形成一个死循环return reject(new TypeError('Type Error,Please....'))}if(x instanceOf MPromise){//如果是promise 肯定有then 方法x.then(y =>{this.resolvePromise(newPromise, y, resolve, reject)}, reject); } else if(typeof x === 'object' || this.isFunction(x)){// typeof null 也是 object,所以需要加判断if(x === null){return resolve(x)}// 按照规范的语义化写法let then = null;try{then = x.then;}catch(error){return reject(error);}if(this.isFunction(then)){// 规范中要求 then 方法 只能被调用一次// 定义一个 called 变量,标识是否被调用let called = false;try{// 为了不发生异常错误,更换then 的 this 指向 为xthen.call(x,(y) =>{if(called){return;}called = true;// 简单的递归,目的就是找到所有的 x this.resolvePromise(newPromise, y, resolve, reject);},(r) =>{if(called){return;}called = true;reject(r);})}catch(error){if(called){return;}reject(error);}}else{resolve(x);}} else {resolve(x)}}isFunction(param){return typeof param === 'function';}
}
9. onFulfilled 和 onRejected 是在微任务中执行的
如何实现?
queueMicrotask(()=>{});传入一个函数,放在微任务里面调用
const PENDING = 'pending';
const FULFILLED = 'fulfilled';
const REJECTED = 'rejected';class MPromise{//直接生命两个数组即可,这里的数组不会被修改 只会被push进来// 状态完成的 listFULFILLED_CALLBACK_LIST = [];// 状态失败的 listREJECTED_CALLBACK_LIST = [];// 存储初始化 status _status = PENDING;constructor(fn){this.status = PENDING;this.value = null;this.reason = null;//需要里面调用,有报错需要立马抛出try{// 考虑严谨性,更改 this 指向为当前环境fn(this.resolve.bind(this), this.reject.bind(this));} catch(e){this.reject(e)}}get status(){// 所有真实的 status return this._status;}set status(newStatus){this._status = newStatus;// 判断不同的状态 执行不同的逻辑switch(newStatus){case FULFILLED: {// then 方法已经判断过是不是function 所以这里不需要判断// 在 status 发生变化的时候,执行对应的回调。this.FULFILLED_CALLBACK_LIST.forEach(callback=>{callback(this.value)});break;}case REJECTED: {this.REJECTED_CALLBACK_LIST.forEach(callback=>{callback(this.reason)});break;}}}resolve(value){// 最终态不可被改变,所以需要加一个判断// 只有当 status 为初始态的时候才可以改变if(this.status === PENDING){this.value = value;this.status = FULFILLED;}}reject(reason){if(this.status === PENDING){this.reason= reason;this.status = REJECTED;}}then(onFulfilled, onRejected){const fulFilledFn = this.isFunction(onFulfilled) ? onFulfilled : (value) => valueconst rejectedFn = this.isFunction(onRejected) ? onRejected : (reason) => throw(reason)//如果 onFulfilled 或者 onRejected 抛出一个异常 e ,那么新的 promise 必须 reject e;const fulFilledFnWitchCatch = (resolve, reject, newPromise) => {queueMicrotask(() => {try{// 不是一个函数 就直接resolve ,因为有返回值了,所以需要判断if(!this.isFunction(onFulfilled)){resolve(this.value)}else{const x = fulFilledFn(this.value);this.resolvePromise(newPromise, x, resolve, reject);}}catch(e) {reject(e)}});}const rejectedFnWitchCatch = (resolve, reject, newPromise) => {queueMicrotask(() => {try{if(!this.isFunction(onRejected)){reject(this.reason);}else{const x = rejectedFn(this.reason);this.resolvePromise(newPromise, x, resolve, reject); }}catch(e) {reject(e)}});}switch(this.status){// then 的返回值是一个promisecase FULFILLED: {const newPromise = new MPromise((resolve, reject) => fulFilledFnWitchCatch(resolve, reject, newPromise));return newPromise;}case REJECTED: {const newPromise = new MPromise((resolve, reject) => rejectedFnWitchCatch(resolve, reject, newPromise));return newPromise;}case PENDING: {const newPromise = new MPromise((resolve, reject) => {this.FULFILLED_CALLBACK_LIST.push(() => fulFilledFnWitchCatch(resolve, reject, newPromise));this.REJECTED_CALLBACK_LIST.push(() => rejectedFnWitchCatch(resolve, reject, newPromise)); });return newPromise;}}}catch(onRejected){return this.then(null, onRejected)}// 规范里定义resolvePromise 需要接受一个 newPromise// resolvePromise 函数的意义,就是对promise 各种值的处理// 让 promise 可以返回一个结果,无论是 resolve 还是 rejectresolvePromise(newPromise, x, resolve, reject){if(newPromise === x){// 返回一个错误信息,信息无所谓什么都可以// 为什么要 reject 一个错误信息,因为如果 newPromise 和 x 相等会相互调用,形成一个死循环return reject(new TypeError('Type Error,Please....'))}if(x instanceOf MPromise){//如果是promise 肯定有then 方法x.then(y =>{this.resolvePromise(newPromise, y, resolve, reject)}, reject); } else if(typeof x === 'object' || this.isFunction(x)){// typeof null 也是 object,所以需要加判断if(x === null){return resolve(x)}// 按照规范的语义化写法let then = null;try{then = x.then;}catch(error){return reject(error);}if(this.isFunction(then)){// 规范中要求 then 方法 只能被调用一次// 定义一个 called 变量,标识是否被调用let called = false;try{// 为了不发生异常错误,更换then 的 this 指向 为xthen.call(x,(y) =>{if(called){return;}called = true;// 简单的递归,目的就是找到所有的 x this.resolvePromise(newPromise, y, resolve, reject);},(r) =>{if(called){return;}called = true;reject(r);})}catch(error){if(called){return;}reject(error);}}else{resolve(x);}} else {resolve(x)}}isFunction(param){return typeof param === 'function';}
}
到这里我们 简单的 promise 已经实现了,可以简单的去测试一下
const test = new MPromise((resolve, reject) => {setTimeout(()=>{resolve(1111);},1000)
}).then(console.log)const test = new MPromise((resolve, reject) => {setTimeout(()=>{reject(1111);},1000)
}).then((value) => {console.log('完成' + value)
}).catch((reason) => {console.log('报错' + reason)
})
到这里 实例方法 resolve reject 已经 加完了,静态方法后期给大家补充;
PromiseA+规范之手写Promise相关推荐
- PromiseA+规范解读手写MyPromsie
PromiseA+规范解读&手写MyPromsie Promise 是什么? 有三种状态 then 手写Promise Promise 是什么? promise 对象 订阅异步回调,在处理异步 ...
- 方法 手写promise_JS探索-手写Promise
无意间在知乎上刷到Monad这个概念,去了解了一下,前端的Promise就是一种Monad模式,所以试着学习一下手写一个Promise. 本文内容主要参考于 只会用?一起来手写一个合乎规范的Promi ...
- 一个下课的时间带你手写promise!
要手写前先看看用法,用法就是我们的需求 //直接调用 let promise=new Promise((resolve,reject)=>{resolve('123') }) promise.t ...
- 手写 Promise
手写 Promise 实现一个简易版 Promise 在完成符合 Promise/A+ 规范的代码之前,我们可以先来实现一个简易版 Promise,因为在面试中,如果你能实现出一个简易版的 Promi ...
- c0语言 测试用例,按照 Promise/A+ 手写Promise,通过promises-aplus-tests的全部872个测试用例...
本文主要讲述如何根据 Promises/A+ 规范,一步步手写一个 Promise 的 polyfill,代码中会配上对应的规范解释. 1. 定义需要的常量和工具方法// 1. 定义表示promsie ...
- 【学习笔记】Part1·JavaScript·深度剖析-函数式编程与 JS 异步编程、手写 Promise(二、JavaScript 异步编程)
[学习笔记]Part1·JavaScript·深度剖析-函数式编程与 JS 异步编程.手写 Promise(课前准备) [学习笔记]Part1·JavaScript·深度剖析-函数式编程与 JS 异步 ...
- 手写Promise和all、race等方法,附上原理解析
手写一个迷你版的Promise JavaScript 中的 Promise 诞生于 ES2015(ES6),是当下前端开发中特别流行的一种异步操作解决方案,简单实现一个迷你版本帮助深入理解 Promi ...
- 按照 Promise/A+ 手写Promise,通过promises-aplus-tests的全部872个测试用例
链接:https://juejin.cn/post/6910500073314975758 本文主要讲述如何根据 Promises/A+ 规范,一步步手写一个 Promise 的 polyfill,代 ...
- javascript --- 手写Promise、快排、冒泡、单例模式+观察者模式
手写promise 一种异步的解决方案, 参考 Promise代码基本结构 function Promise(executor){this.state = 'pending';this.value = ...
最新文章
- Spring Cloud Sleuth 服务跟踪 将跟踪信息存储到数据库
- python小程序源代码-Python数据库小程序源代码
- [architecture]-AMBA AXI AHB APB学习总结
- mysql join 算法_【MySQL】之join算法详解
- ICLR 2021 | 使用CVAE学习干扰集,增强OOD以及对抗防御的能力
- java读取excel中的数据存到数据库
- php基础小结,PHP基础学习小结
- php取到的时间总是差8小时的解决方法
- Kotlin入门(30)多线程交互
- 解决bootstrap-table表头filter-control select控件被遮挡显示不全的问题
- 一例WINDOWS系统上的JAVA UI卡死
- python简单代码-Python中几个非常神奇的代码的简洁,方便,高效!
- Windows命令之ping命令
- 【深度干货】强化学习应用简述
- 基于网络的服装定制MTM系统研究 - 硕士论文 - 道客巴巴
- CAD工程制图基础命令(简洁版)
- 物流管理过程中如何避免客户个人隐私信息泄露
- 数学随想之一抽样分布与总体分布
- 445、Java框架99 -【MyBatis - 多对多】 2020.12.23
- AI+社区智能管理,赋能智慧城市人情共「智」