Promise详解:从回调地狱到优雅异步

Promise 详解

为什么需要 Promise

在实际开发中,我们经常需要处理异步操作链。例如:

  1. 通过 AJAX 请求获取用户 ID
  2. 根据 ID 请求用户名
  3. 根据用户名获取邮箱地址

使用传统回调函数会导致"回调地狱"(回调函数中嵌套回调函数),而 Promise 正是为了解决这个问题而诞生的。

Promise 基本使用

语法

Promise 接受一个函数作为参数,该函数包含两个参数:

  • resolve: 成功回调函数
  • reject: 失败回调函数

Promise 实例

每个 Promise 实例都有两个关键属性:

  • state: 表示当前状态
  • result: 存储操作结果

Promise 的三种状态

  1. pending (等待中)
  2. fulfilled (已成功)
  3. rejected (已失败)

状态改变方法

  • resolve(): 将状态改为 fulfilled
  • reject(): 将状态改为 rejected

注意:Promise 的状态改变是一次性的,不可逆转。

Promise 的方法

then 方法

  • 通过形参获取 Promise 对象的结果
  • 返回一个新的 Promise 实例(初始状态为 pending)
  • 如果 Promise 状态未改变,不会执行 then 中的方法
  • 可以通过 return 将返回的 Promise 实例状态改为 fulfilled
  • 如果代码出错,返回的 Promise 实例状态会改为 rejected

catch 方法

用于捕获和处理错误

async 和 await

async 函数

  • 返回值总是 Promise 对象
  • 结果由函数执行的返回值决定:
    • 返回非 Promise 值:成功状态
    • 返回 Promise 对象:继承该 Promise 的状态
    • 抛出异常:失败状态
javascript 复制代码
async function main() {
  // 1. 返回非 Promise 值(成功状态)
  // return "字符串/数字/布尔值";
  
  // 2. 返回 Promise 对象
  return new Promise((resolve, reject) => {
    resolve("OK"); // 成功状态
    // reject("Err"); // 失败状态
  });
  
  // 3. 抛出异常(失败状态)
  // throw "oh No";
}

await 表达式

  • 右侧表达式通常是 Promise 对象
  • 如果是 Promise 对象,返回其成功值
  • 如果是其他值,直接返回该值

注意事项:

  1. await 必须用在 async 函数中
  2. 如果 await 的 Promise 失败,会抛出异常
  3. 建议使用 try...catch 捕获错误

实践示例

javascript 复制代码
const fs = require("fs");
const util = require("util");
const mineReadFile = util.promisify(fs.readFile); // 转换为 Promise 形式

async function main() {
  try {
    let data1 = await mineReadFile("./resource/1.html");
    let data2 = await mineReadFile("./resource/2.html");
    let data3 = await mineReadFile("./resource/3.html");
  } catch(e) {
    console.log(e);
  }
}
相关推荐
修己xj20 小时前
打造专属博文封面神器:一个开源免费的博文封面生成器ThisCover
前端
kyriewen20 小时前
面试8家前端岗位后,我发现了一个残酷的事实:AI不是加分项,是门槛
前端·javascript·面试
Fighting_p21 小时前
【面试 - el-select问题及解决】wujie 微前端下子系统 el-select 多选 filterable 过滤失效
前端
吃口巧乐兹21 小时前
AI 全栈时代,为什么要服务端使用 NestJs
前端
yingyima21 小时前
Redis 延迟任务队列:凌晨3点服务器报警的救星
前端
weiggle21 小时前
第三篇:可组合函数(Composable)——Compose 的基石
android·前端
前端环境观察室21 小时前
别只看 task success:AI Agent 浏览器自动化真正要补的是环境证据链
前端·后端
huakoh21 小时前
LangChain 实战:用混合检索啃下 1000 页 PDF,搭一个长文档问答 Agent
前端
Dazer00721 小时前
Edge 浏览器绕过 HTTPS 证书错误
前端·https·edge
元让_vincent21 小时前
Spark 2.0:面向 Web 的 3DGS 可视化与大场景渲染平台详解
前端·3d·spark·渲染·轻量化·3dgs·lod