JavaScript 中的 Promise 类

JavaScript 中的 Promise 类

在本文中,我们解释了 JavaScript 中的 Promise 类。

YouTube Video

Promise

Promise 类用于处理异步操作。它处理操作成功时的结果或发生失败时的错误处理。传统上,回调函数被用来等待异步操作完成,但 Promise 使这一过程变得更加清晰和强大。

1const promise = new Promise((resolve, reject) => {
2    setTimeout(() => resolve("Done!"), 1000);
3});
4
5// Displays "Done!" after 1 second
6promise.then(result => console.log(result));
  • 此代码是一个异步处理的示例,在一秒后显示“完成!”。
    • 首先,使用 new Promise 创建一个新的 Promise 对象。参数是一个带有两个回调函数的函数:resolve 表示成功,reject 表示失败。
    • 使用 setTimeout 在一秒后调用 resolve()
    • promise 对象的 then() 方法等待完成并显示结果。

基本结构

Promise 是一个最终会产生成功失败结果的对象。

 1const promise = new Promise((resolve, reject) => {
 2    // Asynchronous operation
 3    // Flag indicating whether the operation was successful
 4    const success = true;
 5
 6    if (success) {
 7        resolve('Operation successful!');
 8    } else {
 9        reject('An error occurred');
10    }
11});
  • 成功时,调用 resolve()
  • 失败时,调用 reject()

Promise 对象有三种状态。

1promise
2    .then((result) => {
3        console.log(result);
4    })
5    .catch((error) => {
6        console.error(error);
7    })
  • 进行中
    • 异步处理尚未完成。
  • 已完成
    • 异步处理成功,结果由 resolve() 返回。使用 then() 方法接收结果。
  • 已拒绝
    • 异步处理失败,通过 reject() 触发错误。使用 catch() 方法接收错误。

then()catch() 方法

通过使用 Promise,可以定义异步操作完成时要执行的操作。为此,可以使用 then()catch() 方法。

then()

1const promise = new Promise((resolve, reject) => {
2    resolve('Operation successful!');
3});
4
5promise.then((result) => {
6    console.log(result);  // "Operation successful!"
7});
  • then() 方法指定了 Promise 成功时要调用的函数。

catch()

1const promise = new Promise((resolve, reject) => {
2    reject('An error occurred');
3});
4
5promise.catch((error) => {
6    console.error(error);  // "An error occurred"
7});
  • catch() 方法指定了 Promise 失败时要调用的函数。

finally() 方法

 1const promise = new Promise((resolve, reject) => {
 2    resolve('Operation successful!');
 3});
 4
 5promise
 6    .then((result) => {
 7        console.log(result);
 8    })
 9    .catch((error) => {
10        console.error(error);
11    })
12    .finally(() => {
13        console.log('The operation has completed');
14    });
  • finally() 方法定义了无论 Promise 是成功还是失败,都会在最后执行的代码。

“then()” 链

then() 会返回一个新的 Promise,因此你可以链式调用下一个 then()

 1const promise = new Promise((resolve, reject) => {
 2    setTimeout(() => {
 3        resolve(1);
 4    }, 1000);
 5});
 6
 7promise
 8    .then(result => {
 9        console.log(result); // 1
10        return result + 1;
11    })
12    .then(result => {
13        console.log(result); // 2
14        return result + 1;
15    })
16    .then(result => {
17        console.log(result); // 3
18    })
19    .catch(error => {
20        console.error(error.message); // Something went wrong
21    });
  • 在此代码中,最初的 resolve() 传递值 1,每个 then 返回的值都会传递给下一个 then
  • 使用 catch(),你可以在一个地方处理链中发生的所有错误。

实际示例

例如,Promises通常用于从服务器获取数据。让我们来看一个使用fetch() API的示例。

 1fetch('https://codesparklab.com/json/example.json')
 2    .then(response => {
 3        if (!response.ok) {
 4            throw new Error('Network error');
 5        }
 6        return response.json();
 7    })
 8    .then(data => {
 9        console.log(data);
10    })
11    .catch(error => {
12        console.error('Error:', error);
13    });
  • 在此代码中,由于fetch()返回一个Promise,因此使用then()在收到服务器响应后处理数据。使用catch()来处理错误。

处理多个Promise

Promise.all()

要同时执行多个Promises,并仅在全部成功时继续,请使用Promise.all()

 1const promise1 = Promise.resolve(1);
 2const promise2 = Promise.resolve(2);
 3const promise3 = Promise.resolve(3);
 4
 5Promise.all([promise1, promise2, promise3])
 6    .then((results) => {
 7        console.log(results);  // [1, 2, 3]
 8    })
 9    .catch((error) => {
10        console.error('Error :', error);
11    });
  • 仅当所有Promises都成功时才调用then()。如果有一个失败,则调用catch()

Promise.allSettled()

如果你想同时运行多个 Promise 并且无论成功或失败都获取所有结果,请使用 Promise.allSettled()

 1const promise1 = Promise.resolve(1);
 2const promise2 = Promise.reject("Failed");
 3const promise3 = Promise.resolve(3);
 4
 5Promise.allSettled([promise1, promise2, promise3])
 6    .then((results) => {
 7        results.forEach(result => console.log(result));
 8        // [
 9        //   { status: 'fulfilled', value: 1 },
10        //   { status: 'rejected', reason: 'Failed' },
11        //   { status: 'fulfilled', value: 3 }
12        // ]
13    });
  • 一旦所有的 Promise 都已完成(无论是已实现还是已拒绝),就会调用 then()。每个结果都包含一个 status 属性('fulfilled' 或 'rejected')。即使有一些失败,也不会影响其他操作。

Promise.race()

Promise.race() 返回最先完成(无论成功还是失败)的 Promise 的结果。

1const promise1 = new Promise((resolve) => setTimeout(resolve, 100, 'First'));
2const promise2 = new Promise((resolve) => setTimeout(resolve, 500, 'Second'));
3
4Promise.race([promise1, promise2]).then((result) => {
5    console.log(result);  // "First"
6});
  • 如同此例,会返回第一个完成的 Promise 的结果。

async/await的关系

使用async/await语法可以更直观地书写Promisesasync函数始终返回一个Promise,而await等待该Promise解决。

 1async function fetchData() {
 2    try {
 3        const response = await fetch('https://codesparklab.com/json/example.json');
 4        const data = await response.json();
 5        console.log(data);
 6    } catch (error) {
 7        console.error('Error :', error);
 8    }
 9}
10
11fetchData();

通过这种方式使用async/await,可以像编写同步代码一样书写异步操作,使其更易于阅读。

总结

  • Promise是一个用于处理异步操作成败的对象。
  • 使用then()处理成功的操作,使用catch()处理错误。
  • finally()定义了无论成功还是失败最终都会执行的代码。
  • 可以使用Promise.all()Promise.race()一起处理多个Promise
  • async/await是更简单书写Promise的语法。

您可以在我们的YouTube频道上使用Visual Studio Code跟随上述文章进行学习。 请也查看我们的YouTube频道。

YouTube Video