📕重学JavaScript:Promise 中的静态方法

简介: 在本次文章中,我们将探讨 Promise API 中的各种静态方法、如何使用它们。

📕重学JavaScript:Promise 中的静态方法

嗨,大家好!这里是道长王jj~ 🎩🧙‍♂️

在本次文章中,我们将探讨 Promise API 中的各种静态方法、如何使用它们。

📌Promise.resolve()

我们之前创建的 Promise 对象都是从 pending 状态开始的,然后在执行器函数里用 resolve()reject() 把它们变成 fulfilledrejected 。但是有时候我们想要直接得到一个 fulfilled 的 Promise 对象,怎么办呢?🤔

这时候就可以用 Promise.resolve() 啦!它可以把任何值变成一个已经 fulfilled 的 Promise 对象。👏


var promise = Promise.resolve( " fulfilled" );
console.log( promise );

// Promise { <state>: "fulfilled", <value>: " fulfilled" }

看,上面的例子里, promise 一出生就是 fulfilled 状态,根本不用等待。👌

Promise.resolve() 很方便,因为它让我们不用写那么多构造函数和执行函数的代码,只要给它一个值,它就会给我们一个 Promise 对象。🎁

📌Promise.reject()

有了 Promise.resolve() ,我们可以直接创建一个 fulfilled 的 Promise 对象,那么有没有办法直接创建一个 rejected 的 Promise 对象呢?🤔

当然有啦!就是 Promise.reject() 。它可以把任何设置的值变成一个已经 rejected 的 Promise 对象。😱


var promise = Promise.reject( "出现错误" );
console.log( promise );

/*
Promise { 
  <state>: "rejected", 
  <reason>: "出现错误" 
}

Uncaught (in promise) 出现错误
*/

看,上面的例子里, promise 一出生就是 rejected 状态,根本不用等待。😢

📌Promise.all()

有时候我们需要等一些 Promise 都完成了才做一些事情,比如买了电影票和爆米花才能看电影。🎬

这时候就可以用 Promise.all() 啦!它可以把一堆 Promise 放在一起,等它们都 fulfilled 了才 fulfilled 。👏

Promise.all() 可以接受一个数组或者一个可迭代的东西,里面放着 1 个或多个 Promise 。

Promise.all() 会返回一个新的 Promise 。如果里面的所有 Promise 都 fulfilled 了,那么这个新的 Promise 也会 fulfilled 。如果里面有任何一个 Promise rejected 了,那么这个新的 Promise 也会 rejected 。😱

这就是为什么 Promise.all() 很适合处理一些需要同时完成的异步操作。🚀

var promise1 = new Promise( (resolve, reject) => {
   
    setTimeout(() => {
   
        resolve( 1 );
    }, 1000);    
});
var promise2 = new Promise( (resolve, reject) => {
   
    setTimeout(() => {
   
        resolve( 2 );
    }, 2000);    
});
var returnedPromise = Promise.all([ promise1, promise2 ]);


console.log( "Initially: ", returnedPromise );


promise1.then( value => {
   
  console.log( " 1:", returnedPromise );
});


promise2.then( value => {
   
  console.log( "2: ", returnedPromise );
});


/*
Initially: Promise { <state>: "pending" }
 1:Promise { <state>: "pending" }
2: Promise {
  <state>: "fulfilled",
  <value>: [ 1, 2 ] 
}
*/

看,上面的例子里, promise1 用了 1 秒才 fulfilled ,值是“1”。但是 Promise.all() 里的 returnedPromise 还没 fulfilled 。它还在等着它的小伙伴 promise2 。当 promise2 用了 2 秒也 fulfilled 了,值是“2”,那么 returnedPromise 就终于 fulfilled 了。👌

returnedPromise 的值是一个数组,里面放着它的小伙伴们的值,这个例子里就是 [ 1, 2 ]

那么如果有一个小伙伴被 rejected 了怎么办呢?🤔

我们来看看下面的例子。

var promise1 = new Promise( (resolve, reject) => {
   
    setTimeout(() => {
   
        resolve( 1 );
    }, 1000);    
});
var promise2 = new Promise( (resolve, reject) => {
   
    setTimeout(() => {
   
        reject( "出现错误" );
    }, 2000);    
});
var promise3 = new Promise( (resolve, reject) => {
   
    setTimeout(() => {
   
        resolve( 3 );
    }, 3000);    
});

var returnedPromise = Promise.all([ promise1, promise2, promise3 ]);

 .
console.log( "Initially: ", returnedPromise );


promise1.then( value => {
   
  console.log( " 1:", returnedPromise );
});

promise2.catch( value => {
   
  console.log( "2: ", returnedPromise );
});

promise3.then( value => {
   
  console.log( "3: ", returnedPromise );
});

/*
Initially: Promise { <state>: "pending" }

 1:Promise { <state>: "pending" }

2: Promise { 
  <state>: "rejected", 
  <reason>: "出现错误" 
}
Uncaught (in promise) 出现错误

3: Promise { 
  <state>: "rejected", 
  <reason>: "出现错误" 
}
*/

看,上面的例子里, promise1 用了 1 秒才 fulfilled 。这时候, returnedPromise 还在等着它的小伙伴们 promise2promise3 。但是 promise2rejected 了。😱

这就让 returnedPromise 也被 rejected 了,原因跟 promise2 一样。

而且, Promise.all() 不会管 promise3 的结果。它只要看到有一个小伙伴被 rejected 了,就马上把自己也变成 rejected ,这就叫做短路。🔥

有一个特别的情况,就是给 Promise.all() 一个空数组。这时候, Promise.all() 会返回一个已经 fulfilled 的 Promise ,值是一个空数组。👍

var returnedPromise = Promise.all( [] );
console.log( returnedPromise );

// Promise { <state>: "fulfilled", <value>: [] }

我们之前看到,返回的 Promise 一般都要等一会儿才 fulfilledrejected 。但是在上面的例子里, returnedPromise 一出生就是 fulfilled ,它不用等待。👌

这是因为它的小伙伴们都是空的,所以它也没什么可等的。😅

这是 Promise.all() 唯一会同步返回一个已经 fulfilledrejected 的 Promise 的情况,其他情况下,它都会返回一个要异步等待的 Promise 。🚀

📌Promise.allSettled()

我们刚刚看到, Promise.all() 会在有一个小伙伴被 rejected 了就短路。但是有时候我们不想这样,我们想要等所有的小伙伴都完成了才做一些事情,不管它们是 fulfilled 还是 rejected 。🤔

这时候就可以用 Promise.allSettled() 啦!它会等所有的异步操作都结束了才结束。👏

就算有一个小伙伴被 rejected 了,它也不会短路,它会继续等着其他的小伙伴。😊

这就是为什么 Promise.allSettled() 很适合处理一些不需要互相依赖的异步操作。🚀

Promise.allSettled() 也可以接受一个数组或者一个可迭代的东西,里面放着 1 个或多个 Promise 。

Promise.allSettled() 也会返回一个新的 Promise 。🎁

var promise1 = new Promise( (resolve, reject) => {
   
    setTimeout(() => {
   
        resolve( 1 );
    }, 1000);    
});
var promise2 = new Promise( (resolve, reject) => {
   
    setTimeout(() => {
   
        reject( "出现错误" );
    }, 2000);    
});
var promise3 = new Promise( (resolve, reject) => {
   
    setTimeout(() => {
   
        resolve( 3 );
    }, 3000);    
});

var returnedPromise = Promise.allSettled([ promise1, promise2, promise3 ]);


console.log( "Initially: ", returnedPromise );


promise1.then( value => {
   
  console.log( " 1:", returnedPromise );
});

promise2.catch( value => {
   
  console.log( "2: ", returnedPromise );
});

promise3.then( value => {
   
  console.log( "3: ", returnedPromise );
});

/*

Initially: Promise { <state>: "pending" }

 1:Promise { <state>: "pending" }

2: Promise { <state>: "pending" }

3: Promise { 
  <state>: "fulfilled", 
  <value>: [
    { "status": "fulfilled", "value": 1 },
    { "status": "rejected", "reason": "出现错误" },
    { "status": "fulfilled", "value": 3 }
  ]
}

*/

看,上面的例子里, promise2rejected 了,但是 returnedPromise 没有被 rejected 。它还在等着它的小伙伴 promise3 。当三个小伙伴都结束了, returnedPromise 就终于 fulfilled 了。👌

还有一点不同,就是 returnedPromise 的值不是一个简单的数组,里面放着它的小伙伴们的值。它是一个对象数组,每个对象都表示一个小伙伴的状态。如果小伙伴是 fulfilled 的,那么对象里就有 statusvalue 。如果小伙伴是 rejected 的,那么对象里就有 statusreason 。😊

所以,在 Promise.allSettled() 的情况下,返回的 Promise 总是会 fulfilled 。就算所有的小伙伴都被 rejected 了,返回的 Promise 也会通过一个表示每个被 rejected 的小伙伴的对象数组来 fulfilled 。👍

如果我们给 Promise.allSettled() 一个空数组,那么它就跟 Promise.all() 一样,会(同步)返回一个已经 fulfilled 的 Promise ,值是一个空数组。其他情况下,它会返回一个要异步等待的 Promise 。🚀

📌Promise.race()

Promise.race() 的意思就是让一堆 Promise 跑步比赛,谁跑得最快谁就赢了。🏃‍♂️

这里的赢了是指 Promise.race() 不会管其他的 Promise ,只要有一个 Promise 结束了,它就跟着结束。🏁

如果第一个结束的 Promise 是 fulfilled 的,那么 Promise.race() 也会 fulfilled ,值跟它一样。如果第一个结束的 Promise 是 rejected 的,那么 Promise.race() 也会 rejected ,原因跟它一样。😱

Promise.race() 也可以接受一个数组或者一个可迭代的东西,里面放着 1 个或多个 Promise 。

Promise.race() 也会返回一个新的 Promise 。🎁

var promise1 = Promise.resolve( 1 );
var promise2 = new Promise( (resolve, reject) => {
   
    setTimeout(() => {
   
        resolve( 2 );
    }, 1000);    
});

var returnedPromise = Promise.race([ promise1, promise2 ]);

promise1.then( value => {
   
  console.log( " 1:", returnedPromise );
});

/*
 1: 
Promise { <state>: "fulfilled", <value>: 1 }
*/

看,上面的例子里, promise1fulfilled 了,所以 Promise.race() 不会管 promise2 ,就跟着 fulfilled 了,值跟它一样。👌

如果我们把上面的例子里的 Promise.resolve() 换成 Promise.reject() ,那么 promise1 就会被 rejected 了,但是它还是第一个结束的。所以 Promise.race() 也会被 rejected 了,原因跟它一样。😢

如果我们给 Promise.race() 一个空数组,那么它会返回一个永远不会结束的 Promise ,因为它没有小伙伴可以跟着。😅

📌Promise.any()

Promise.any() 的意思就是让一堆 Promise 跑步比赛,谁跑得最快且是 fulfilled 的谁就赢了。🏃‍♀️

这里的赢了是指 Promise.any() 不会管其他的 Promise ,只要有一个 Promise 是 fulfilled 的,它就跟着 fulfilled 。🏁

如果第一个是 fulfilled 的 Promise ,那么 Promise.any() 也会 fulfilled ,值跟它一样。👏

Promise.race() 不一样的是, Promise.any() 不会管被 rejected 的小伙伴,它只在乎 fulfilled 的小伙伴。😊

如果没有一个小伙伴是 fulfilled 的,或者所有的小伙伴都被 rejected 了,那么 Promise.any() 就会抛出一个错误,叫做 AggregateError ,它会把所有的错误都放在一起。😱


🎉 你觉得怎么样?这篇文章可以给你带来帮助吗?当你处于这个阶段时,你发现什么对你帮助最大?如果你有任何疑问或者想进一步讨论相关话题,请随时发表评论分享您的想法,让其他人从中受益。🚀✨

目录
相关文章
|
6天前
|
前端开发 JavaScript
如何处理 JavaScript 中的异步操作和 Promise?
如何处理 JavaScript 中的异步操作和 Promise?
16 1
|
6天前
|
前端开发 JavaScript
在JavaScript中,什么是promise、怎么使用promise、怎么手写promise
在JavaScript中,什么是promise、怎么使用promise、怎么手写promise
29 4
|
6天前
|
前端开发 JavaScript 开发者
JavaScript 中的异步编程:Promise 和 Async/Await
在现代的 JavaScript 开发中,异步编程是至关重要的。本文将介绍 JavaScript 中的异步编程概念,重点讨论 Promise 和 Async/Await 这两种常见的处理异步操作的方法。通过本文的阐述,读者将能够更好地理解和应用这些技术,提高自己在 JavaScript 开发中处理异步任务的能力。
|
6天前
|
JSON 前端开发 JavaScript
【JavaScript技术专栏】JavaScript异步编程:Promise、async/await解析
【4月更文挑战第30天】JavaScript中的异步编程通过Promise和async/await来解决回调地狱问题。Promise代表可能完成或拒绝的异步操作,有pending、fulfilled和rejected三种状态。它支持链式调用和Promise.all()、Promise.race()等方法。async/await是ES8引入的语法糖,允许异步代码以同步风格编写,提高可读性和可维护性。两者结合使用能更高效地处理非阻塞操作。
|
4天前
|
前端开发 JavaScript
前端 js 经典:Promise
前端 js 经典:Promise
10 1
|
6天前
|
前端开发 JavaScript
在JavaScript中,回调函数、Promise和async/await这三种异步处理机制的优缺点
JavaScript的异步处理包括回调函数、Promise和async/await。回调函数简单易懂,但可能导致回调地狱和错误处理困难。Promise通过链式调用改善了这一情况,但仍有回调函数需求和学习成本。async/await提供同步风格代码,增强可读性和错误处理,但需ES8支持,不适用于并发执行。根据项目需求选择合适机制。
|
6天前
|
前端开发 JavaScript
js开发:请解释Promise是什么,以及它如何解决回调地狱(callback hell)问题。
Promise是JavaScript解决异步操作回调地狱的工具,代表未来可能完成的值。传统的回调函数嵌套导致代码难以维护,而Promise通过链式调用`.then()`和`.catch()`使异步流程清晰扁平。每个异步操作封装为Promise,成功时`.then()`传递结果,出错时`.catch()`捕获异常。ES6的`async/await`进一步简化Promise的使用,使异步代码更接近同步风格。
23 1
|
6天前
|
前端开发 JavaScript API
JavaScript学习笔记(一)promise与async
JavaScript学习笔记(一)promise与async
|
6天前
|
前端开发 JavaScript UED
JavaScript中的异步编程和Promise
【2月更文挑战第3天】在Web开发中,JavaScript是一门非常重要的编程语言,而异步编程是JavaScript中的一个关键概念。本文将介绍JavaScript中的异步编程特点,以及如何使用Promise来更加优雅地处理异步操作,帮助开发者更好地理解和应用这一技术。
19 3
|
6天前
|
前端开发 JavaScript 数据处理
JavaScript中的异步编程及Promise对象
【2月更文挑战第3天】 传统的JavaScript编程模式在处理异步任务时常常会导致回调地狱和代码可读性较差的问题,而Promise对象的引入为解决这一问题提供了一种优雅的解决方案。本文将介绍JavaScript中的异步编程方式以及Promise对象的使用方法和优势,帮助读者更好地理解和运用异步编程技术。
22 8