发布于 2026-01-05 10 阅读
0

图解 JS:Mux 呈现的 DEV 全球展示挑战赛承诺:展示你的项目!

图解 JavaScript:Promises

由 Mux 主办的 DEV 全球展示挑战赛:展示你的项目!

在学习 JavaScript 和编程的过程中,我发现用类比的方式来理解概念很有帮助。这里我将分享一个关于 JavaScript 中 Promise 的类比。欢迎在评论区补充。

在 JavaScript 中,如果我们想在异步函数返回后才调用另一个函数,可以使用回调函数。假设我正在烤一个巧克力糖霜蛋糕,那么我的bakeCake()函数是异步的,它接受prepareIcing()一个参数(这就是回调函数),并且只有在蛋糕完全烤好后才会调用它。

画的是一位负责烤蛋糕的面包师,他正在给负责准备糖霜的人打电话。


图 1 - 负责烘焙蛋糕的烘焙师在烘焙完成后调用负责糖霜准备的函数。

但本文我们将重点讨论如何使用Promise。那么 Promise 如何帮助我们解决这个问题呢?Promise 是一个封装了异步操作的对象,如果操作成功,它会被赋值;如果操作失败,它会被拒绝并返回一个原因。这样,我就可以为某个未来才会出现的值(或原因)添加一个处理程序。

一位面包师说:听起来很复杂,对吧?我们先从一个简单的蛋糕开始吧。


图2——我的面包师喜欢用蛋糕来解释各种事情。

回到烘焙的例子,我可以说我的烤箱就像一个蛋糕的承诺,因为它封装了我的烘焙蛋糕操作,并且一开始处于待处理状态(仍在烘焙)。但我有一个智能烤箱,它会在操作完成后通知我。如果烘焙成功,承诺就会兑现,得到一个蛋糕。否则,承诺就会被拒绝,并显示蛋糕烤焦或其他失败原因。

烤箱示意图及蛋糕承诺的可能状态


图 3 - 烤箱代表着一个蛋糕的承诺,它从待定状态开始,并让我知道它何时实现(成功蛋糕)或被拒绝(失败蛋糕)。

正如我们之前所说,使用 Promise,我们可以为其最终状态(成功或失败)添加处理程序。该.then()方法可以同时处理成功和失败(失败的情况较少见),而该.catch()方法只能处理失败。

如果我要烤一个简单的蛋糕(不加糖霜),我会这样处理:如果成功了,我就把蛋糕端上桌。但如果烤糊了,我可以失败的蛋糕捡起来扔进垃圾桶,然后点个派当甜点。😂

绘制烤箱示意图以及蛋糕承诺的可能状态,包括成功处理程序 (serveCake()) 和失败处理程序 (orderPie())


图 4 - 如果 cakeBake() 函数执行成功,调用成功处理函数 serveCake()。否则,捕获失败原因(蛋糕烤焦了),并调用失败处理函数 orderPie()。

另一点需要注意的是,由于一个 Promise 会返回另一个 Promise,因此它们可以链式调用。在我之前提到的蛋糕加糖霜的例子中,我可以先烤好蛋糕,然后准备糖霜,最后蛋糕和糖霜都准备好后,再给蛋糕涂上糖霜。在这种情况下,如果链中的任何一个 Promise 失败,我只需处理一次catch 语句就能处理所有拒绝,然后继续订购一个派。

描绘连锁承诺和成功与失败的操纵者


图 5 - 使用 .then() 和 catch() 链式调用 Promise 来处理成功和失败

但有一种更好的方法可以实现我们在上一个例子中所做的操作。我bakeCake()的两个prepareIcing()函数是独立的,这意味着它们可以同时执行。为此,我们可以使用Promise.all()等待两个结果(蛋糕和糖霜)都得到后再执行coverCake()函数。

承诺的图画示例


图 6 - Promise.all() 在覆盖蛋糕之前,同时处理蛋糕本身的承诺和糖霜的承诺。

在内部Promise.all(),如果其中任何一个承诺被拒绝(失败),那么整个承诺都会被拒绝。这很合理,对吧?如果蛋糕或糖霜缺失,我就无法盖住整个蛋糕。

以上是对 Promise 概念及其使用方法的非常简化和概括的解释.then()希望足够清晰易懂。.catch()Promise.all()

感谢阅读,欢迎在评论区留言。我保证下一篇文章已经在酝酿中了(待定)。完成后我会第一时间在推特上分享,如果被拒稿,我就发些猫咪照片。

本文要点:

  • Promise 是封装异步操作的对象。
  • 承诺始于待定状态,在未来的某个时刻,它们会变为已履行(成功)或已拒绝(失败)状态。
  • Promise 会返回一个新的 Promise,该 Promise 可以用于链式调用。
  • .then()我们可以使用`or`在操作返回时为成功值或失败原因添加处理程序.catch()
  • Promise.all()等待所有承诺都得到解决。如果任何承诺被拒绝,则该承诺被拒绝。

参考文献和推荐延伸阅读

文章来源:https://dev.to/marinafroes/illusterated-js-promises-5ed7