目录
一、promise的基本使用
1.应用场景:
Promise是一个类,可以翻译成 承诺、许诺 、期约; 当我们需要给予调用者一个承诺:待会儿我会给你回调数据时,就可以创建一个Promise的对象;
2.executor
在通过new创建Promise对象时,我们需要传入一个回调函数,我们称之为executor
-
通常我们会在Executor中确定我们的Promise状态:
-
通过resolve,可以兑现(fulfilled)Promise的状态,我们也可以称之为已决议(resolved)
-
通过reject,可以拒绝(reject)Promise的状态;
-
-
注意:一旦状态被确定下来,Promise的状态会被 锁死,该Promise的状态是不可更改的
-
在我们调用resolve的时候,如果resolve传入的值本身不是一个Promise,那么会将该Promise的状态变成 兑 现(fulfilled)
-
在之后我们去调用reject时,已经不会有任何的响应了(并不是这行代码不会执行,而是无法改变Promise状 态);
-
3.Promise的三种状态
-
待定(pending): 初始状态,既没有被兑现,也没有被拒绝;
-
当执行executor中的代码时,处于该状态;
-
-
已兑现(fulfilled/resolve): 意味着操作成功完成;
-
执行了resolve时,处于该状态;
-
-
已拒绝(rejected): 意味着操作失败;
-
执行了reject时,处于该状态;
-
代码示例:
// 注意:Promise状态一旦被确定下来 就不可以更改
new Promise((resolve, reject) => {
// pending状态 初始状态,既没有被兑现,也没有被拒绝
console.log("---------------");
// fulfilled状态 已兑现,意味着操作成功完成
// resolve()
// rejected状态 意味着操作失败
}).then(res => {
console.log(res);
}, err => {
console.log(err);
})
二、Promise的resolve参数
区别:
-
情况一:如果resolve传入一个普通的值或者对象,那么这个值会作为then回调的参数;
-
情况二:如果resolve中传入的是另外一个Promise,那么这个新Promise会决定原Promise的状态:
-
情况三:如果resolve中传入的是一个对象,并且这个对象有实现then方法,那么会执行该then方法,并且根据 then方法的结果来决定Promise的状态
代码示例:
/**
* resolve参数
* 1> 普通的值或对象 pending -> fulfilled
* 2> 传入一个Promise
* 那么当前Promise的状态会由传入的Promise来决定
* 相当于状态进行了移交
* 3> 传入一个对象,并且这个对象有实现then的方法(并且这个对象是实现了thenable接口)
* 那么也会执行该then方法,并且又该then方法决定后续状态
*/
// 一个新的Promise对象
const newPromise = new Promise((resolve, reject) => {
// resolve("bbbb")
// reject("err")
})
new Promise((resolve,reject) => {
// 1.普通的值或对象
resolve("aaaa")
// resolve({name: 'kk'})
// 2.传入一个Promise
// resolve(newPromise)
// 3.传入一个对象,并且这个对象有实现then的方法
// const obj = {
// then: function(resolve, reject) {
// resolve("resolve message")
// }
// }
// resolve(obj)
}).then(res => {
console.log("res:", res);
}, err => {
console.log("err:", err);
})
三、Promise的对象方法(实例方法)
1.then方法
then方法是Promise对象上的一个方法:它其实是放在Promise的原型上的 Promise.prototype.then
1.2 then可以被多次调用
一个Promise的then方法是可以被多次调用的:
-
每次调用我们都可以传入对应的fulfilled回调;
-
当Promise的状态变成fulfilled的时候,这些回调函数都会被执行;
代码示例:
// then方法可以被多次调用
// 当Promise的状态变成fulfilled的时候,这些回调函数都会被执行
const promise = new Promise((reslove, reject) => {
reslove('111111')
})
promise.then(res => {
console.log(res);
})
promise.then(res => {
console.log(res);
})
promise.then(res => {
console.log(res);
})
1.3 then方法的返回值
then传入的回调函数可以有返回值(它的返回值是一个新的Promise对象)
- 当then方法中的回调函数本身在执行的时候,那么它处于pending状态;
- 当then方法中的回调函数返回一个结果时,那么它处于fulfilled状态,并且会将结果作为resolve的参数
三种情况:
如果我们的返回值是一个普通值(数值/字符串/普通对象/undefined),那么这个普通的值被作为一个新的Promise的resolve值
const promise = new Promise((resolve, reject) => {
resolve()
})
promise.then(() => {
return 'aaaaa' //这里会返回一个新的Promise对象 Promise((resolve,reject) => { resolve('aaaaa') })
}).then(res => {
console.log('res:', res);
})
如果返回一个Promise
promise.then(res => {
return new Promise((resolve, reject) => {
setTimeout(() => {
resolve('11111')
},3000)
}) // 返回一个新的Promise对象 Promise((resolve, reject) => { resolve(new Promise) }) 于是resolve(Promise)里面的Promise的reslove决定了外面的res输出值
}).then(res => {
console.log("res:", res);
})
如果返回的是一个对象 并且该对象实现了thenable
promise.then(res => {
return {
then: function(resolve, reject) {
resolve(22222)
}
}
}).then(res => {
console.log("res:", res);
})
2.catch方法
2.1 基本使用
catch会查看promise是否是rejected状态,是就返回,否则,查看then方法是否返回一个新的promise对象,且新的promise对象是rejected状态
const promise = new Promise((resolve, reject) => {
resolve()
// reject("reject status")
// throw new Error("rejected status")
})
// 1.当executor抛出异常时也是会调错误(拒绝)捕获回调函数的
promise.then(undefined, err => {
console.log("err:", err);
})
// 2.通过catch方法来传入错误(拒绝)捕获回调函数
promise.catch(err => {
console.log("err:", err);
})
promise.then(res => {
// return new Promise((resolve, reject) => {
// reject("then rejected status")
// })
throw new Error("error message")
}).catch(err => {
console.log("err:", err); // err: reject status 这里的catch是外面第一个promise的方法 调用外面的reject
// 如果外面的promise没有没有异常,而then返回的promise有异常 catch也会帮助找到这个promise异常 然后输出
})
2.2 catch特殊
当promise里没有reject(), catch就会找到下面then返回的promise,找到里面的reject,并打印
const promise = new Promise((resolve, reject) => {
// reject(111111)
resolve()
})
promise.then(res => {
return new Promise((resolve, reject) => {
reject(222222)
})
}).catch(err => {
console.log(err);
})
2.3 catch的返回值
事实上catch方法也是会返回一个Promise对象的,所以catch方法后面我们可以继续调用then方法或者catch方法: 是res打印,这是因为catch传入的回调在执行完后,默认状态依然会是fulfilled的;
const promise = new Promise((resolve, reject) => {
// reject(111111)
resolve()
})
promise.then(res => {
return new Promise((resolve, reject) => {
reject(222222)
})
}).catch(err => {
console.log(err);
return "catch return value"
}).then(res => {
}).catch(err => {
})
3. finally方法
无论Promise对象无论变成fulfilled还是reject状态,最终都会 被执行的代码。且finally方法是不接收参数的,因为无论前面是fulfilled状态,还是reject状态,它都会执行。
代码示例:
const promise = new Promise((resolve, reject) => {
resolve()
})
promise.then(res => {
console.log(res);
}).catch(err => {
console.log(err);
}).finally(() => {
console.log("finally action");
})
四、Promise的类方法
1.reslove类方法
resolve参数的形态:
-
情况一:参数是一个普通的值或者对象
-
情况二:参数本身是Promise
-
情况三:参数是一个thenable
Promise.resolve("zyk").then(res => {
console.log(res);
})
// 相当于
const promise = new Promise((resolve, reject) => {
resolve("zyk")
})
promise.then(res => {
console.log(res);
})
2. reject类方法
reject方法类似于resolve方法,只是会将Promise对象的状态设置为reject状态
Promise.reject传入的参数无论是什么形态,都会直接作为reject状态的参数传递到catch的
// 注意:无论传入什么值都是一样的
const promise = Promise.reject(new Promise((reslove, reject) => {reslove(11111)})) // Promise { 11111 }
promise.then(res => {
console.log(res);
}).catch(err => {
console.log(err);
})
// 相当于
// const promise = new Promise((reslove, reject) => {
// reslove(11111)
// })
// promise.then(res => {
// console.log(res);
// }).catch(err => {
// console.log(err);
// })
3. all类方法
-
它的作用是将多个Promise包裹在一起形成一个新的Promise;
-
新的Promise状态由包裹的所有Promise共同决定:
-
当所有的Promise状态变成fulfilled状态时,新的Promise状态为fulfilled,并且会将所有Promise的返回值 组成一个数组;
-
当有一个Promise状态为reject时,新的Promise状态为reject,并且会将第一个reject的返回值作为参数;
-
-
缺陷 :当有其中一个Promise变成reject状态时,新Promise就会立即变成对应的reject状态。 那么对于resolved的,以及依然处于pending状态的Promise,我们是获取不到对应的结果的;
const p1 = new Promise((reslove, reject) => {
setTimeout(() => {
reslove(11111)
}, 1000)
})
const p2 = new Promise((reslove, reject) => {
setTimeout(() => {
// reslove(22222)
reject("err message")
}, 2000)
})
const p3 = new Promise((reslove, reject) => {
setTimeout(() => {
reslove(33333)
}, 3000)
})
// 需求:将所有的Promise都变成fulfilled状态,再难道结果
// 意外:在拿到所有结果之前 如果有一个promise变为reject, 那么整个promi都是rejected状态的
// all相当于返回一个新的Promise 然后Promise(reslove(all里面的参数))
Promise.all([p1, p2, p3, "aaaaa"]).then(res => {
console.log(res);
}).catch(err => {
console.log(err);
})
4. allSettled类方法
该方法会在所有的Promise都有结果(settled),无论是fulfilled,还是reject时,才会有最终的状态,并且这个Promise的结果一定是fulfilled的;
const p1 = new Promise((reslove, reject) => {
setTimeout(() => {
reslove(11111)
}, 1000)
})
const p2 = new Promise((reslove, reject) => {
setTimeout(() => {
// reslove(22222)
reject("err message")
}, 2000)
})
const p3 = new Promise((reslove, reject) => {
setTimeout(() => {
reslove(33333)
}, 3000)
})
Promise.allSettled([p1, p2, p3]).then(res => {
console.log(res);
}).catch(err => {
console.log(err);
})
/**
* 打印结果
* [
{ status: 'fulfilled', value: 11111 },
{ status: 'rejected', reason: 'err message' },
{ status: 'fulfilled', value: 33333 }
]
*/
5. race类方法
只要有一个Promise编程fulfilled状态,那么就结束,但是,如果有一个Promise最快变为reject 那么就执行catch
const p1 = new Promise((reslove, reject) => {
setTimeout(() => {
reslove(11111)
}, 1000)
})
const p2 = new Promise((reslove, reject) => {
setTimeout(() => {
// reslove(22222)
reject("err message")
}, 500)
})
const p3 = new Promise((reslove, reject) => {
setTimeout(() => {
reslove(33333)
}, 3000)
})
// race: 竞赛
// 只要有一个Promise编程fulfilled状态,那么就结束
// 意外:如果有一个Promise最快变为reject 那么就执行catch
Promise.race([p1, p2, p3]).then(res => {
console.log(res);
}).catch(err => {
console.log(err);
})
6. any类方法
它会等有一个最快的fulfilled状态,然后就返回其Promise的值,如果全部都为reject 他会返回 AggregateError: All promises were rejected
const p1 = new Promise((reslove, reject) => {
setTimeout(() => {
reject(11111)
}, 1000)
})
const p2 = new Promise((reslove, reject) => {
setTimeout(() => {
// reslove(22222)
reject("err message")
}, 500)
})
const p3 = new Promise((reslove, reject) => {
setTimeout(() => {
reject(33333)
}, 3000)
})
// 他会等有一个最快的fulfilled状态,然后就返回其Promise的值
// 如果全部都为reject 他会返回 AggregateError: All promises were rejected
Promise.any([p1, p2, p3]).then(res => {
console.log(res);
}).catch(err => {
console.log(err);
})