news 2026/5/16 20:49:05

JavaScript 异步(Promise)

作者头像

张小明

前端开发工程师

1.2k 24
文章封面图
JavaScript 异步(Promise)

本文全面讲解 Promise:创建、链式调用、组合、错误处理与常见陷阱,是前端异步编程的核心标准。


你是否想过:

如何表示一个暂时还不存在的值?如何告别深层嵌套回调,写出近乎同步写法的异步代码?

// 回调地狱 getUser(userId, function(user) { getPosts(user.id, function(posts) { getComments(posts[0].id, function(comments) { console.log(comments) }) }) }) // Promise 扁平写法 getUser(userId) .then(user => getPosts(user.id)) .then(posts => getComments(posts[0].id)) .then(comments => console.log(comments))

Promise是代表异步操作最终完成 / 失败的对象,ES2015(ES6)标准化。你可以把它理解为:餐厅取餐号—— 现在没食物,但承诺做好后给你结果。


本文你将学到

  • Promise 是什么、为何诞生
  • 三种状态:pending /fulfilled/rejected
  • 用构造函数创建 Promise
  • 使用.then()/.catch()/.finally()
  • Promise 链式调用原理
  • 所有静态方法:all /allSettled/race /any/resolve /reject/withResolvers /try
  • 常用模式与避坑指南

前置知识:回调函数(Callback)


一、什么是 Promise?

Promise 是一个代表异步操作最终结果的 JS 对象。它的含义:我现在没有值,但我保证之后给你结果(或错误)

// 1秒后决议的 Promise const promise = new Promise((resolve, reject) => { setTimeout(() => { resolve('Hello from the future!') }, 1000) }) promise.then(value => { console.log(value) // 1秒后输出 })

与回调不同:Promise 是返回的对象,而非传入的函数。这让链式调用、组合、统一错误处理成为可能。


二、餐厅取餐类比

  • 你下单 → 调用异步函数
  • 拿到取餐号 →得到 Promise 对象
  • 等待做菜 →pending(进行中)
  • 餐做好 →fulfilled(成功)
  • 食材用完 →rejected(失败)
  • 取餐 →.then()
  • 处理问题 →.catch()

关键特性:一旦落定(settled),状态永久不变


三、为什么需要 Promise?(回调的问题)

  • 嵌套地狱(金字塔代码)
  • 错误处理分散、重复
  • 无法组合并行 / 串行流程
  • 同步 / 异步行为不一致

Promise 提供:

  • 扁平链式结构
  • 统一错误捕获
  • 强大的并发控制
  • 确定性异步行为

四、Promise 三态与命运

三种状态(State)

  1. pending:初始状态,进行中
  2. fulfilled:成功,有结果值
  3. rejected:失败,有错误原因

重要规则

  • 一旦从 pending → fulfilled /rejected,状态永久锁定
  • resolve()/reject()多次调用只生效第一次

命运(Fate)

  • resolved:命运已锁定(可能仍 pending,但会跟随内部 Promise)
  • unresolved:未锁定

五、Thenable 对象

任何拥有.then()方法的对象都叫thenable。JS 会自动把它当作 Promise 兼容处理,实现库间互操作。

const thenable = { then(onFulfilled) { onFulfilled(42) } } Promise.resolve(thenable).then(console.log) // 42

六、创建 Promise

1. 构造函数

const p = new Promise((resolve, reject) => { // 同步立即执行 // 成功 → resolve(value) // 失败 → reject(error) })

2. 包装回调式 API

function loadImage(url) { return new Promise((resolve, reject) => { const img = new Image() img.onload = () => resolve(img) img.onerror = () => reject(new Error('load failed')) img.src = url }) }

3. 快速创建

Promise.resolve(值) Promise.reject(错误)

七、消费 Promise:then /catch/finally

1..then()

核心方法,接收成功回调,返回新 Promise

2..catch()

捕获链中任何错误,等价于.then(undefined, err => {})

3..finally()

无论成功 / 失败都会执行,用于清理(关闭加载、释放资源)。


八、Promise 链式调用(核心能力)

每一个.then()返回新 Promise,形成扁平流程。

Promise.resolve(1) .then(x => x + 1) // 2 .then(x => x + 1) // 3 .then(console.log)

规则:

  • 返回普通值 → 作为下一个 then 的值
  • 返回 Promise → 等待它决议再继续
  • 抛出错误 → 进入最近 catch

九、错误处理(超级强大)

  • 错误会自动穿透整条链,直到被 catch
  • 一个 catch 捕获所有上游错误
  • 可 catch 后恢复流程
getUser() .then(user => getPosts(user.id)) .then(posts => getComments(posts[0].id)) .catch(err => console.error('任意一步出错:', err))

十、Promise 静态方法(必背)

1.Promise.all([])

  • 全部成功才成功
  • 任意失败立即失败(短路)
  • 并行执行,等待全部

2.Promise.allSettled([])

  • 永远不失败
  • 等待全部落定
  • 返回每个结果的状态与值

3.Promise.race([])

  • 先落定谁赢
  • 成功失败都算结束
  • 常用于超时控制

4.Promise.any([])

  • 先成功谁赢
  • 忽略失败
  • 全部失败才返回 AggregateError

5.Promise.withResolvers()(ES2024)

直接外部获取 resolve/reject,更简洁。

const { promise, resolve, reject } = Promise.withResolvers()

6.Promise.try()(Baseline 2025)

统一处理同步 / 异步函数,捕获同步抛出。


十一、常用异步模式

1. 串行执行(依赖前序结果)

for...of + await

2. 并行执行(互不依赖)

Promise.all

3. 分批并行(防限流)

slice + 循环 + Promise.all

4. 重试机制

循环 + catch + delay

5. 回调转 Promise(Promisify)

包装成 (resolve, reject) 形式


十二、常见错误(高频坑)

  1. 忘记 return→ 链断裂、undefined
  2. 嵌套而非链式→ 重回回调地狱
  3. new Promise 包裹已有 Promise(反模式)
  4. 没有 catch→ 未处理拒绝崩溃 / 警告
  5. forEach + async→ 不等待,直接继续
  6. 微任务时序误解:then 永远在同步代码之后

十三、核心要点总结

  • Promise = 异步结果占位符
  • 三态:pending → fulfilled /rejected
  • 一旦落定,不可改变
  • then 返回新 Promise → 支持链式
  • 错误自动穿透,一个 catch 搞定
  • 并行 / 竞速 / 超时 / 重试都靠静态方法
  • 是 async/await 的基础

概念 汇总

一、核心基础

  1. Promise同类:Future、Deferred、异步契约、Task
  2. 异步占位值同类:延迟计算、未来值
  3. Promise 状态(pending/fulfilled/rejected)同类:异步生命周期、操作状态机
  4. 落定(settled)同类:决议、完成、结束

二、语法与 API

  1. thenable同类:类 Promise 对象、鸭子类型
  2. Promise 链式调用同类:流式调用、管道流程
  3. .then() / .catch() / .finally()同类:回调处理器、完成钩子、清理函数

三、静态组合方法

  1. Promise.all同类:并行等待、全部成功、并发汇聚
  2. Promise.allSettled同类:容忍失败并行、结果收集、批量状态
  3. Promise.race同类:竞速、抢先完成、超时机制
  4. Promise.any同类:优先成功、多源备选、最快可用
  5. Promise.withResolvers同类:延迟决议、外部控制 Promise
  6. Promise.try同类:统一同步异步、安全执行包裹

四、模式与问题

  1. 回调地狱同类:嵌套金字塔、厄运金字塔
  2. Promise 构造反模式同类:多余包装、冗余封装
  3. 未处理 Promise 拒绝同类:未捕获异常、崩溃隐患
  4. 微任务时序同类:事件循环、任务队列、宏任务 / 微任务

五、上层抽象

  1. async/await同类:Promise 语法糖、线性异步写法
  2. 并行 / 串行 / 分批同类:并发控制、任务调度、限流
  3. 重试(Retry)同类:容错、退避重试、故障自动恢复

版权声明: 本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若内容造成侵权/违法违规/事实不符,请联系邮箱:809451989@qq.com进行投诉反馈,一经查实,立即删除!
网站建设 2026/5/16 20:48:08

初创公司如何利用taotoken快速低成本验证多个大模型产品创意

🚀 告别海外账号与网络限制!稳定直连全球优质大模型,限时半价接入中。 👉 点击领取海量免费额度 初创公司如何利用 Taotoken 快速低成本验证多个大模型产品创意 对于资源有限的初创团队而言,验证一个融合多种 AI 能力…

作者头像 李华
网站建设 2026/5/16 20:43:16

30秒上手AI视频插帧:用Flowframes让视频帧率翻倍的终极指南

30秒上手AI视频插帧:用Flowframes让视频帧率翻倍的终极指南 【免费下载链接】flowframes Flowframes Windows GUI for video interpolation using DAIN (NCNN) or RIFE (CUDA/NCNN) 项目地址: https://gitcode.com/gh_mirrors/fl/flowframes 想要让普通视频瞬…

作者头像 李华
网站建设 2026/5/16 20:39:46

C#基础IO11

一、IO概念1。概念:I/O:Input/Output,即输入和输出 C# 的 I/O 操作主要围绕 控制台输入输出(一般数据显示到控制台,注意格式化) 和 文件输入输出(即文件的读写操作)。2。I/O 重要的类…

作者头像 李华
网站建设 2026/5/16 20:39:03

AI Agent Harness Engineering 在法律行业的应用前景

AI Agent Harness Engineering 在法律行业的应用前景:从“黑盒子智能”到“可信任法律伙伴”的破局之路 摘要 (全文约12500字,其中核心章节要素完整覆盖,兼顾行业痛点、技术原理、实战应用、未来趋势等维度) AI Agent&…

作者头像 李华
网站建设 2026/5/16 20:36:47

Step-by-Step知识蒸馏:让小模型学会大模型的推理思维

1. 项目概述:当“蒸馏”遇上“分步走”最近在模型压缩和知识蒸馏的圈子里,一个挺有意思的讨论点又热了起来:我们是不是把“蒸馏”这件事想得太“一锤子买卖”了?传统思路里,老师模型(大模型)和学…

作者头像 李华