首页 > web前端 > js教程 > 正文

JavaScript 中的 Promise:初学者终极指南

PHPz
发布: 2024-07-28 06:36:23
原创
814 人浏览过

Promises in JavaScript: The Ultimate Guide for Beginners

介绍

JavaScript 是一种多功能编程语言,主要用于 Web 开发。 JavaScript 最强大的功能之一是它处理异步操作的能力。这就是 Promise 发挥作用的地方,它允许开发人员更有效地管理异步代码。本指南将带您了解 Promise 的基础知识,提供深入的知识和实际示例,帮助您理解和有效地利用它们。

目录

Heading Subtopics
What is a Promise in JavaScript? Definition, State of a Promise, Basic Syntax
Creating a Promise Example, Resolving, Rejecting
Chaining Promises then(), catch(), finally()
Handling Errors Common Pitfalls, Error Handling Techniques
Promise.all() Usage, Examples, Handling Multiple Promises
Promise.race() Usage, Examples, First Settled Promise
Promise.any() Usage, Examples, First Fulfilled Promise
Promise.allSettled() Usage, Examples, When All Promises Settle
Async/Await Syntax, Combining with Promises, Examples
Real-World Examples Fetch API, Async File Reading
Common Mistakes Anti-Patterns, Best Practices
Advanced Promise Concepts Custom Promises, Promise Combinators
FAQs Answering Common Questions
Conclusion Summary, Final Thoughts

JavaScript 中的 Promise 是什么?

JavaScript 中的 Promise 是一个表示异步操作最终完成或失败的对象。它允许您将处理程序与异步操作的最终成功值或失败原因相关联。这使得异步方法能够像同步方法一样返回值:异步方法不是立即返回最终值,而是返回一个在未来某个时刻提供该值的承诺。

承诺的状态

承诺可以处于以下三种状态之一:

  1. 待处理:初始状态,既不满足也不拒绝。
  2. 已完成:操作成功完成。
  3. 已拒绝:操作失败。

Promise 的基本语法

let promise = new Promise(function(resolve, reject) {
    // Asynchronous operation
    let success = true;

    if(success) {
        resolve("Operation successful!");
    } else {
        reject("Operation failed!");
    }
});
登录后复制

创造一个承诺

创建 Promise 涉及实例化一个新的 Promise 对象并向其传递一个函数。该函数有两个参数:resolve 和reject。

例子

let myPromise = new Promise((resolve, reject) => {
    let condition = true;
    if(condition) {
        resolve("Promise resolved successfully!");
    } else {
        reject("Promise rejected.");
    }
});

myPromise.then((message) => {
    console.log(message);
}).catch((message) => {
    console.log(message);
});
登录后复制

在此示例中,myPromise 将成功解析并记录“Promise已成功解析!”到控制台。

链接承诺

Promise 的强大功能之一是能够链接它们。这允许您以可读且可维护的方式执行一系列异步操作。

然后()

then() 方法用于处理承诺的履行。

myPromise.then((message) => {
    console.log(message);
    return "Next step";
}).then((nextMessage) => {
    console.log(nextMessage);
});
登录后复制

抓住()

catch() 方法用于处理承诺的拒绝。

myPromise.then((message) => {
    console.log(message);
}).catch((error) => {
    console.log(error);
});
登录后复制

最后()

finally() 方法用于执行代码,无论 Promise 是履行还是拒绝。

myPromise.finally(() => {
    console.log("Promise is settled (either fulfilled or rejected).");
});
登录后复制

处理错误

处理 Promise 中的错误对于健壮的代码至关重要。

常见陷阱

  1. 忽略错误:始终使用catch() 处理错误。
  2. 忘记返回:确保在 then() 处理程序中返回承诺。

错误处理技术

myPromise.then((message) => {
    console.log(message);
    throw new Error("Something went wrong!");
}).catch((error) => {
    console.error(error.message);
});
登录后复制

Promise.all()

Promise.all() 接受一个 Promise 数组并返回一个单个 Promise,当数组中的所有 Promise 都解析时,该 Promise 会解析;如果任何一个 Promise 被拒绝,则该 Promise 会被拒绝。

用法

let promise1 = Promise.resolve(3);
let promise2 = 42;
let promise3 = new Promise((resolve, reject) => {
    setTimeout(resolve, 100, 'foo');
});

Promise.all([promise1, promise2, promise3]).then((values) => {
    console.log(values); // [3, 42, "foo"]
});
登录后复制

Promise.race()

Promise.race() 返回一个 Promise,只要数组中的一个 Promise 解析或拒绝,该 Promise 就会解析或拒绝。

用法

let promise1 = new Promise((resolve, reject) => {
    setTimeout(resolve, 500, 'one');
});
let promise2 = new Promise((resolve, reject) => {
    setTimeout(resolve, 100, 'two');
});

Promise.race([promise1, promise2]).then((value) => {
    console.log(value); // "two"
});
登录后复制

Promise.any()

Promise.any() 返回一个 Promise,只要数组中的任何一个 Promise 满足,该 Promise 就会解析;如果所有 Promise 都被拒绝,则该 Promise 会被拒绝。

用法

let promise1 = Promise.reject("Error 1");
let promise2 = new Promise((resolve, reject) => setTimeout(resolve, 100, "Success"));
let promise3 = new Promise((resolve, reject) => setTimeout(resolve, 200, "Another success"));

Promise.any([promise1, promise2, promise3]).then((value) => {
    console.log(value); // "Success"
}).catch((error) => {
    console.log(error);
});
登录后复制

Promise.allSettled()

Promise.allSettled() 返回一个在所有给定的 Promise 都已解决或拒绝后解析的 Promise,其中包含一个对象数组,每个对象都描述每个 Promise 的结果。

用法

let promise1 = Promise.resolve("Resolved");
let promise2 = Promise.reject("Rejected");

Promise.allSettled([promise1, promise2]).then((results) => {
    results.forEach((result) => console.log(result.status));
});
登录后复制

异步/等待

async 和await 关键字允许您以更同步的方式使用promise。

句法

async function myFunction() {
    let myPromise = new Promise((resolve, reject) => {
        setTimeout(() => resolve("Done!"), 1000);
    });

    let result = await myPromise; // Wait until the promise resolves
    console.log(result); // "Done!"
}

myFunction();
登录后复制

与 Promise 结合

async function fetchData() {
    try {
        let response = await fetch('https://api.example.com/data');
        let data = await response.json();
        console.log(data);
    } catch (error) {
        console.error("Error fetching data: ", error);
    }
}

fetchData();
登录后复制

现实世界的例子

获取API

Fetch API 是 Promise 的常见用例。

fetch('https://api.example.com/data')
    .then(response => response.json())
    .then(data => console.log(data))
    .catch(error => console.error('Error:', error));
登录后复制

异步文件读取

在 Node.js 中使用 Promise 读取文件。

const fs = require('fs').promises;

async function readFile() {
    try {
        let content = await fs.readFile('example.txt', 'utf-8');
        console.log(content);
    } catch (error) {
        console.error('Error reading file:', error);
    }
}

readFile();
登录后复制

常见错误

反模式

  1. 回调地狱:避免嵌套 then() 调用。
  2. 忽略错误:始终处理承诺拒绝。

最佳实践

  1. 始终返回 Promise:确保在 then() 和 catch() 处理程序中返回 Promise。
  2. 使用 Async/Await:使用 async 和 wait 简化 Promise 处理。

先进的承诺概念

定制承诺

您可以创建自定义 Promise 来处理特定的异步操作。

function customPromiseOperation() {
    return new Promise((resolve, reject) => {
        setTimeout(() => {
            resolve("Custom operation complete!");
        }, 2000);
    });
}

customPromiseOperation().then((message) => {
    console.log(message);
});
登录后复制

Promise 组合器

使用 Promise.all()、Promise.race() 等组合器组合多个 Promise,以处理复杂的异步流程。

常见问题解答

Promise 如何帮助异步编程?
与传统回调相比,Promise 提供了一种更清晰、更易读的方式来处理异步操作,从而降低了“回调地狱”的风险。

then() 和 `

有什么区别

catch()?
then() 用于处理已解决的 Promise,而 catch()` 用于处理被拒绝的 Promise。

你可以在较旧的 JavaScript 代码中使用 Promise 吗?
是的,Promise 可以与较旧的 JavaScript 代码一起使用,但为了完全兼容,您可能需要使用 polyfill。

使用 Promise.all() 有什么好处?
Promise.all() 允许您并行运行多个 Promise 并等待所有这些 Promise 完成,从而更轻松地管理多个异步操作。

async/await 如何改进 Promise 处理?
async/await 语法使异步代码的外观和行为更像同步代码,从而提高了可读性和可维护性。

如果承诺既没有得到解决也没有被拒绝会发生什么?
如果一个 Promise 既没有被解决也没有被拒绝,它就会无限期地保持在待处理状态。重要的是要确保所有承诺最终得到解决或拒绝,以避免潜在的问题。

结论

Promise 是现代 JavaScript 的基本组成部分,使开发人员能够更高效、更易读地处理异步操作。通过掌握 Promise,您可以编写更清晰、更易于维护的代码,从而有效地处理异步编程的复杂性。无论您是从 API 获取数据、读取文件还是执行自定义异步任务,理解 Promise 对于任何 JavaScript 开发人员来说都是至关重要的。

以上是JavaScript 中的 Promise:初学者终极指南的详细内容。更多信息请关注PHP中文网其他相关文章!

来源:dev.to
本站声明
本文内容由网友自发贡献,版权归原作者所有,本站不承担相应法律责任。如您发现有涉嫌抄袭侵权的内容,请联系admin@php.cn
热门教程
更多>
最新下载
更多>
网站特效
网站源码
网站素材
前端模板
关于我们 免责声明 Sitemap
PHP中文网:公益在线PHP培训,帮助PHP学习者快速成长!