Promise一直都有在用,但是也就停留在會用,會調(diào)其幾個api上。
本文再次梳理一下Promise知識點,爭取做到知其所以然。
首先,Promise是一個對象,那么我們先把其實例創(chuàng)建出來:
const promise = new Promise(function(resolve, reject){
//①
if (/* 異步操作成功 */) {
resolve(value);//value就是異步請求拿到的結(jié)果
} else {
reject(error);
}
})
我們可以看到,Promise構(gòu)造函數(shù)接受一個函數(shù)作為參數(shù),該函數(shù)的兩個參數(shù)分別是resolve和reject。它們是兩個函數(shù),由JavaScript引擎提供,不用自己去定義。(resolve、reject這兩個方法名是約定俗成的)
我們用Promise的目的有兩個:一是發(fā)起異步請求的,二是拿到請求結(jié)果去做一些其他操作。
Promise構(gòu)造函數(shù)接收的這個參數(shù)就可以滿足我們這兩個需求,一我們的的異步請求在參數(shù)內(nèi)部①處發(fā)起,然后拿到結(jié)果之后通過resolve/reject函數(shù)給它傳出去。
注1:resolve()調(diào)用了之后,Promise的狀態(tài)就由pending=>fulfilled;reject()調(diào)用了之后,Promise的狀態(tài)就由pending=>rejected;狀態(tài)變更了之后我們就可以調(diào)用Promise.prototype.then()了。
注2:Promise new了之后①中的代碼就會立即執(zhí)行
然后then()登場了,
then(resolve,reject)
then接收兩個回調(diào)函數(shù)作為參數(shù),resolve是必傳,reject是可選
注3:這里的resolve和reject的需要自己定義的,名字也不一定是resolve,reject(可以是then(xxx,xxxx)),只不過這兩個名字也是約定俗成的。
注4:這里的執(zhí)行順序也需要留意一下:
let promise = new Promise(function(resolve, reject){
console.log(1);
resolve()
});
promise.then(() => console.log(2));
console.log(3)
//1 3 2
在Promise new之后會立即執(zhí)行,所以首先輸出 1 。然后,then方法指定的回調(diào)函數(shù)將在當(dāng)前腳本所有同步任務(wù)執(zhí)行完后才會執(zhí)行,所以 2 最后輸出。
注3:reject回調(diào)和catch區(qū)別:reject后的東西,一定會進(jìn)入then中的第二個回調(diào),如果then中沒有寫第二個回調(diào),則進(jìn)入catch
有些錯誤(比如斷網(wǎng)等)只會進(jìn)入catch而不進(jìn)入第二個回調(diào)
Promise靜態(tài)方法:
Promise.resolve和Promise.reject
輔助創(chuàng)建 resolved 和 reject 方法:
const p1 = Promise.resolve("success!!!!")
p1.then(function(res){
console.log(res)
})
Promise.all
let p1 = new Promise((resolve, reject) => {
resolve('成功了')
})
let p2 = new Promise((resolve, reject) => {
resolve('success')
})
let p3 = Promse.reject('失敗')
Promise.all([p1, p2]).then((result) => {
console.log(result) //['成功了', 'success']
}).catch((error) => {
console.log(error)
})
Promise.all([p1,p3,p2]).then((result) => {
console.log(result)
}).catch((error) => {
console.log(error) // '失敗' 有一個失敗就返回reject傳回的信息
})
Promise.race
賽跑,顧名思義,返回最快返回結(jié)果的那個promise的值,不管是成功還是失敗哦
let p1 = new Promise((resolve, reject) => {
setTimeout(() => {
resolve('成功')
},1000)
})
let p2 = new Promise((resolve, reject) => {
setTimeout(() => {
reject('失敗')
}, 500)
})
Promise.race([p1, p2]).then((result) => {
console.log(result)
}).catch((error) => {
console.log(error) // '失敗'
})
手寫Promise
async/await
async修飾的函數(shù)會返回一個Promise對象
eg:
async function test() {
return "=_=";
}
const result = test();
console.log(result); //Promise {<fulfilled>: "=_="}
如果在函數(shù)中 return 一個直接量,async 會把這個直接量通過** Promise.resolve()** 封裝成 Promise 對象;
如果沒return,那么返回Promise {<fulfilled>: undefined}