ES8 异步解决方案 Async 和 Await 讲解

前言

在 JavaScript 中,异步编程是非常常见的,比如网络请求、文件读写、定时器等等。异步编程可以提高程序的响应速度,但同时也会带来一些问题,比如回调地狱、代码可读性差等等。为了解决这些问题,ES8(也称为 ECMAScript 2017)引入了 Async 和 Await,这是一种更加优雅、简单的异步编程解决方案。

Async 和 Await 是什么?

Async 和 Await 是 ES8 引入的两个新关键字。在 ES8 之前,异步编程主要使用回调函数、Promise 等方式实现。而 Async 和 Await 的出现,使得异步编程更加简单、易读、易维护。

Async 和 Await 的实现依赖于 Promise,因此在学习 Async 和 Await 之前,建议先了解一下 Promise。

Async 函数

Async 函数是一个返回 Promise 对象的异步函数。它的语法如下:

async function foo() {
  // 异步操作
  return result;
}

Async 函数可以包含多个异步操作,每个异步操作都可以使用 await 关键字等待其完成。在 Async 函数中,使用 return 返回的值会被包装成一个 Promise 对象。

下面是一个简单的示例:

async function getData() {
  let result = await fetch('https://api.example.com/data');
  let data = await result.json();
  return data;
}

getData().then(data => {
  console.log(data);
});

在上面的示例中,getData 函数是一个 Async 函数,它包含了两个异步操作:

  1. 发送一个 GET 请求,获取数据。
  2. 将获取的数据解析为 JSON 格式。

使用 await 关键字可以让这些异步操作变得像同步操作一样,代码也更加易读。最后,使用 Promise 的 then 方法获取 getData 函数返回的数据。

Await 关键字

Await 是 Async 函数中用来等待异步操作完成的关键字。它只能在 Async 函数中使用。

当 await 关键字后面跟着一个 Promise 对象时,它会暂停 Async 函数的执行,直到该 Promise 对象状态变为 resolved(已完成)或 rejected(已拒绝)。

下面是一个示例:

async function foo() {
  console.log('start');
  await new Promise(resolve => setTimeout(resolve, 1000));
  console.log('end');
}

foo();

在上面的示例中,foo 函数包含了一个异步操作,即等待 1 秒钟(使用 setTimeout 模拟)。使用 await 关键字可以让这个异步操作变得像同步操作一样,不会阻塞后续代码的执行。

错误处理

在 Async 函数中,如果某个异步操作发生错误,可以使用 try...catch 语句来捕获错误。如果 Async 函数中发生了错误,并且没有使用 try...catch 语句来捕获错误,那么该错误会被包装成一个 rejected 状态的 Promise 对象,从而导致后续代码无法执行。

下面是一个示例:

async function foo() {
  try {
    let result = await fetch('https://api.example.com/data');
    let data = await result.json();
    return data;
  } catch (err) {
    console.error(err);
  }
}

foo().then(data => {
  console.log(data);
});

在上面的示例中,如果网络请求发生错误,try...catch 语句会捕获该错误,并输出到控制台。由于使用了 try...catch 语句,后续代码仍然可以执行。

总结

Async 和 Await 是 ES8 引入的两个新关键字,它们可以使异步编程更加简单、易读、易维护。Async 函数是一个返回 Promise 对象的异步函数,它可以包含多个异步操作,每个异步操作都可以使用 await 关键字等待其完成。如果 Async 函数中发生了错误,可以使用 try...catch 语句来捕获错误。

来源:JavaScript中文网 ,转载请注明来源 本文地址:https://www.javascriptcn.com/post/65be9b7fadd4f0e0ff822b5c