async 函數是什么?一句話,它就是 Generator 函數的語法糖,async 函數的實現原理,就是將 Generator 函數和自動執行器,包裝在一個函數里。
1,Generator 函數
const fs = require('fs');
const readFile = function (fileName) {
return new Promise(function (resolve, reject) {
fs.readFile(fileName, function(error, data) {
if (error) return reject(error);
resolve(data);
});
});
};
const gen = function* () {
const f1 = yield readFile('/etc/fstab');
const f2 = yield readFile('/etc/shells');
console.log(f1.toString());
console.log(f2.toString());
};
轉換成async是:
const asyncReadFile = async function () {
const f1 = await readFile('/etc/fstab');
const f2 = await readFile('/etc/shells');
console.log(f1.toString());
console.log(f2.toString());
};
一比較就會發現,async函數就是將 Generator 函數的星號(*)替換成async,將yield替換成await,僅此而已。
async只不過將Generator進行了一些改進;
2,async具體使用和優點
async函數返回一個 Promise 對象,可以使用then方法添加回調函數。當函數執行的時候,一旦遇到await就會先返回,等到異步操作完成,再接着執行函數體內后面的語句。
function timeout(ms) {
return new Promise((resolve) => {
setTimeout(resolve, ms);
});
}
async function asyncPrint(value, ms) {
await timeout(ms);
console.log(value);
}
asyncPrint('hello world', 50);
上面代碼指定 50 毫秒以后,輸出hello world。
async異步函數變體:
異步函數聲明: async function foo() {}
異步函數表達式: const foo = async function () {};
異步函數定義:let obj = { async foo() {} }
異步箭頭函數: const foo = async () => {};
理解:
-
async 表示這是一個 async 函數,而 await 只能在這個函數里面使用。
-
await 表示在這里等待 await 后面的操作執行完畢,再執行下一句代碼。
-
await 后面緊跟着的最好是一個耗時的操作或者是一個異步操作(當然非耗時的操作也可以的,但是就失去意義了)。
3,錯誤處理
如果await后面的異步操作出錯,那么等同於async函數返回的 Promise 對象被reject。
async function f() {
await new Promise(function (resolve, reject) {
throw new Error('出錯了');
});
}
f()
.then(v => console.log(v))
.catch(e => console.log(e))
// Error:出錯了
防止出錯的方法,也是將其放在try...catch代碼塊之中。
async function main() {
try {
const val1 = await firstStep();
const val2 = await secondStep(val1);
const val3 = await thirdStep(val1, val2);
console.log('Final: ', val3);
}
catch (err) {
console.error(err);
}
}
說白了async也是一個Promis對象,我們可以在async后面加上then或者catch這個東西來防止出錯。
轉載於:https://www.cnblogs.com/luozhixiang/p/9116965.html
