async
作為一個(gè)關(guān)鍵字放在函數(shù)的前面忘瓦,表示該函數(shù)是一個(gè)異步函數(shù)器联,意味著該函數(shù)的執(zhí)行不會(huì)阻塞后面代碼的執(zhí)行 異步函數(shù)的調(diào)用跟普通函數(shù)一樣
async function timeout(){
return "helloworld";
}
console.log(timeout());
console.log("我在異步函數(shù)后面,會(huì)先執(zhí)行誰呢");
// Promise { 'helloworld' }
// 我在異步函數(shù)后面,會(huì)先執(zhí)行誰呢
可以看出執(zhí)行順序還是函數(shù)先執(zhí)行愈污,但是函數(shù)的返回結(jié)果是一個(gè)Promise對(duì)象,要獲取Promise的返回值應(yīng)該用then方法
async function timeout(){
return "helloworld";
}
timeout().then((result)=>{
console.log(result);
});
console.log("我在異步函數(shù)后面轮傍,會(huì)先執(zhí)行誰呢");
// 我在異步函數(shù)后面暂雹,會(huì)先執(zhí)行誰呢
// helloworld
此時(shí)先輸出的就是后面的一串文字,說明異步函數(shù)的執(zhí)行沒有阻塞后面的代碼執(zhí)行创夜,
async
的內(nèi)部實(shí)現(xiàn)原理就是如果該函數(shù)中有一個(gè)返回值杭跪,當(dāng)調(diào)用該函數(shù)時(shí),默認(rèn)會(huì)在內(nèi)部調(diào)用Promise.solve()
方法把它轉(zhuǎn)化成一個(gè)Promise
對(duì)象作為返回驰吓,若函數(shù)內(nèi)部拋出錯(cuò)誤涧尿,則調(diào)用Promise.reject()
返回一個(gè)Promise
對(duì)象
async function timeout1(flag){
if(flag){
return "hello world";
}else{
throw new Error("error!!");
}
}
console.log(timeout1(true));
console.log(timeout1(false));
// Promise {<resolved>: "hello world"}
// Promise {<rejected>: Error: error!!...}
既然
async
返回的是一個(gè)Promise
對(duì)象,那么Promise
的所有用法他都可以用檬贰,如Promise.catch
捕獲異常等
await
await
即等待现斋,用于等待一個(gè)Promise
對(duì)象。它只能在異步函數(shù)async function
中使用偎蘸,否則會(huì)報(bào)錯(cuò)
它的返回值不是Promise
對(duì)象而是Promise
對(duì)象處理之后的結(jié)果
await
表達(dá)式會(huì)暫停當(dāng)前async function
的執(zhí)行庄蹋,等待Promise
處理完成。若Promise
正常處理(fulfilled)
迷雪,其回調(diào)的resolve
函數(shù)參數(shù)作為await
表達(dá)式的值限书,繼續(xù)執(zhí)行async function
,若Promise
處理異常(rejected)
章咧,await
表達(dá)式會(huì)把Promise
的異常原因拋出倦西。?如果await
操作符后的表達(dá)式的值不是一個(gè)Promise
,那么該值將被轉(zhuǎn)換為一個(gè)已正常處理的Promise
赁严。
與Promise對(duì)比
1扰柠、不再需要多層.then方法
假設(shè)一個(gè)業(yè)務(wù)分很多步驟完成,并且每個(gè)步驟都是異步疼约,依賴上一個(gè)步驟的結(jié)果卤档。
function takeLongTime(n) {
return new Promise(resolve => {
setTimeout(() => resolve(n + 200), n);
});
}
function step1(n) {
console.log(`step1 with ${n}`);
return takeLongTime(n);
}
function step2(n) {
console.log(`step2 with ${n}`);
return takeLongTime(n);
}
function step3(n) {
console.log(`step3 with ${n}`);
return takeLongTime(n);
}
// Promise方式
function doIt() {
console.time("doIt");
const time1 = 300;
step1(time1)
.then(time2 => step2(time2))
.then(time3 => step3(time3))
.then(result => {
console.log(`result is ${result}`);
console.timeEnd("doIt");
});
}
doIt();
// async await方式
async function doIt() {
console.time("doIt");
const time1 = 300;
const time2 = await step1(time1);
const time3 = await step2(time2);
const result = await step3(time3);
console.log(`result is ${result}`);
console.timeEnd("doIt");
}
doIt();
2、可以對(duì)Promise進(jìn)行并行處理