什么是 `async/await` 及其如何工作,有什么优缺点

什么是 async/await 及其如何工作,有什么优缺点?

介绍

async/await 是一种建立在Promise之上的编写异步或非阻塞代码的新方法,被普遍认为是 JS异步操作的最终且最优雅的解决方案。相对于 Promise 和回调,它的可读性和简洁度都更高。

async 是异步的意思,而 awaitasync wait的简写,即异步等待。

所以从语义上就很好理解 async 用于声明一个 function 是异步的,而await 用于等待一个异步方法执行完成。

一个函数如果加上 async ,那么该函数就会返回一个 Promise

async function test() {
     
  return "1"
}
console.log(test()) // -> Promise {: "1"}

可以看到输出的是一个Promise对象。所以,async 函数返回的是一个 Promise 对象,如果在 async 函数中直接 return 一个直接量,async 会把这个直接量通过 PromIse.resolve()封装成Promise对象返回。

async/await 能更好地处理 then 链

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);
}

现在分别用 Promiseasync/await来实现这三个步骤的处理。

使用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}`);
        });
}
doIt();
// step1 with 300
// step2 with 500
// step3 with 700
// result is 900

使用 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}`);
}
doIt();

结果和之前的 Promise 实现是一样的,但是这个代码看起来是不是清晰得多,优雅整洁,几乎跟同步代码一样。

await关键字只能在async function中使用。在任何非async function的函数中使用await关键字都会抛出错误。await关键字在执行下一行代码之前等待右侧表达式(可能是一个Promise)返回。

优缺点:

async/await 的优势在于处理 then 的调用链,能够更清晰准确的写出代码,并且也能优雅地解决回调地狱问题。当然也存在一些缺点,因为 await 将异步代码改造成了同步代码,如果多个异步代码没有依赖性却使用了 await 会导致性能上的降低。

你可能感兴趣的:(JavaScript,promise,async/await)