Promise
js
Promise.myResolve = function (value) {
// 是Promise实例,直接返回即可
if (value && typeof value === 'object' && (value instanceof Promise)) {
return value
}
// 否则其他情况一律再通过Promise包装一下
return new Promise((resolve) => {
resolve(value)
})
}
Promise.myReject = function (value) {
return new Promise((_, reject) => {
reject(value)
})
}
/**
* 最终p的状态由p1、p2、p3决定,分成两种情况。
* (1)只有p1、p2、p3的状态都变成fulfilled,p的状态才会变成fulfilled,此时p1、p2、p3的返回值组成一个数组,传递给p的回调函数。
* (2)只要p1、p2、p3之中有一个被rejected,p的状态就变成rejected,此时第一个被reject的实例的返回值,会传递给p的回调函数。
*
* @param promises
* @returns {Promise<unknown>}
*/
Promise.myAll = function (promises) {
return new Promise((resolve, reject) => {
let count = 0;
let result = []
if (promises.length === 0) return resolve([]);
promises.forEach(promise => {
promise.resolve(promise).then((res) => {
count += 1;
result[i] = res;
if (count === promise.length) {
resolve(result)
}
}).catch(err)
})
})
}
/**
* Promise.allSettled()方法接受一个数组作为参数,数组的每个成员都是一个 Promise 对象,并返回一个新的 Promise 对象。
* 只有等到参数数组的所有 Promise 对象都发生状态变更(不管是fulfilled还是rejected),返回的 Promise 对象才会发生状态变更,一旦发生状态变更,
* 状态总是fulfilled,不会变成rejected
*
* @param promises
* @returns {Promise<unknown>}
*/
Promise.myAllSettled = (promises) => {
return new Promise((rs, rj) => {
let count = 0
let result = []
const len = promises.length
// 数组是空的话,直接返回空数据
if (len === 0) {
return rs([])
}
promises.forEach((p, i) => {
Promise.resolve(p).then((res) => {
count += 1
// 成功属性设置
result[ i ] = {
status: 'fulfilled',
value: res
}
if (count === len) {
rs(result)
}
}).catch((err) => {
count += 1
// 失败属性设置
result[i] = {
status: 'rejected',
reason: err
}
if (count === len) {
rs(result)
}
})
})
})
}
/**
* Promise.race()方法同样是将多个 Promise 实例,包装成一个新的 Promise 实例。
* 只要p1、p2、p3之中有一个实例率先改变状态,p的状态就跟着改变。那个率先改变的 Promise 实例的返回值,就传递给p的回调函数
* @param promises
* @returns {Promise<unknown>}
*/
Promise.myRace = (promises) => {
return new Promise((rs, rj) => {
promises.forEach((p) => {
// 对p进行一次包装,防止非Promise对象
// 并且对齐进行监听,将我们自己返回的Promise的resolve,reject传递给p,哪个先改变状态,我们返回的Promise也将会是什么状态
Promise.resolve(p).then(rs).catch(rj)
})
})
}