重学前端-Promise用法详解

前言

在JavaScript的世界中,Promise毫无疑问是里程碑式的一个变革,它不仅解决了异步编程中,回调函数嵌套过深的问题,还为Async/Await奠定了基础。

Promise规范最早由CommonJS社区提出,后来成为ES2015(ES6)语言规范,到现在可以说已经成了异步编程的首选方案。
接下来本文将详细讲解Promise的特性和方法,供各位大大们参考,如果文中有不正确的地方,欢迎大家斧正。
话不多说,上才艺!

正文

1、构造函数Promise(excutor)

  • excutor:
    • Promise构造函数接受一个执行器作为参数(excutor,其实就是一个回调函数),在Promise构造函数执行时,会立即执行传入的excutor。
    • excutor函数被调用时,会传入resolve, reject两个函数作为参数;当resolve函数被调用,Promise状态变更为fulfilled(完成);当reject函数被调用,Promise状态变更为rejected(失败)
    • 如果excutor内部抛出异常,Promise状态将直接变更为rejected,错误对象将作为结果返回。 javascript const p = new Promise((resolve, reject) => { console.log("excutor函数会被立即执行"); resolve("状态变更为:fulfilled"); // reject("状态变更为:rejected"); // throw new Error('报错,Promise状态将直接变更为rejected') });

      2、状态

Promise一共有3中状态:

  • *pending: *初始状态,既不是成功,也不是失败
  • *fulfilled: *成功
  • rejected: 失败

    3、实例方法

- then(onFulfilled, onRejected)
  • 作用:
    • 为Promise注册onFulfilled和onRejected回调
    • 返回新的promise,实现链式调用
    • 新的promise将以回调函数返回值来resolve
  • 特性:
    • then方法本身会自动返回一个新的Promise对象,当然也可以手动在任意(onFulfilled或者onRejected)回调函数中返回一个Promise对象 ```javascript const p = new Promise((resolve, reject) => { console.log("excutor函数会被立即执行"); resolve("状态变更为:fulfilled"); });

// then方法本身会返回一个promise p.then() .then() .then((res) => { console.log(res); //输出:状态变更为:fulfilled }); // then方法通过回调函数可以返回promise p.then( (res) => { return new Promise((resolve, reject) => { resolve("onFulfilled中返回的Promise"); }); }, (reason) => { return new Promise((resolve, reject) => { resolve("onRejected回调中也可以返回Promise"); }); } ).then((res) => { console.log(res); }); ```

  • then方法可以通过返回的Promise对象,实现链式调用
  • 如果回调函数返回的是普通值,那么将会在下一个then中作为回调函数参数被接收
  • 如果回调函数返回的是一个Promise, 下一个then方法将会等待这个Promise执行结束,并接收Promise的执行结果 javascript const p2 = new Promise((resolve, reject) => { console.log("excutor函数会被立即执行"); resolve("状态变更为:fulfilled"); }); p2.then(res => { return new Promise((resolve, reject) => { setTimeout(() => { resolve('promise执行完毕') }, 1000); }) }).then(res => { console.log(res)//等待1秒钟,输出:promise执行完毕 })

  • 如果没有传入回调函数,Promise将自动为then方法注册回调函数,并在回调函数中将接收到的值返回,传递给下一个then,实现值的穿透。 ```javascript 没有给then注册回调,发生值穿透 const p3 = new Promise((resolve, reject) => { resolve(1); }); p3.then(2).then(4).then(console.log); //1

```

  • then方法中不允许将本身返回的promise对象作为返回值 ```javascript const p4 = p3.then(res => { // 不允许,将会报错 // TypeError: Chaining cycle detected for promise # return p4 })

```

- catch(onRejected)
  • 作用
    • 给Promise添加onRejected回调
  • 特性

    • 返回一个新的Promise
    • 新的Promise将以回调函数返回值来resolve javascript const promise = new Promise((resolve, reject) => { reject(100); }); promise .catch((reason) => { console.log(reason); //100 return 200; //catch函数返回值将作为新Promise的resolve结果 }) .then((res) => { // 新Promise执行结果 console.log(res); //200 });
      - finally(finallyCallback)
  • 作用

    • 给Promise添加一个事件处理回调函数
  • 特性
    • 无论成功还是失败,都会调用传入的finallyCallback
    • finallyCallback会返回一个新的Promise
    • finallyCallback内部不能获取到Promise执行结果 ```javascript const promise = new Promise((resolve, reject) => { resolve(100); }); promise .finally((res) => { console.log("finally回调函数无论成功或者失败,始终会被执行"); // finally回调函数内获取不到promise执行结果 console.log(res); }) .then((res) => { // finally回调函数返回一个新的promise,实现链式调用 console.log(res); });

```

4、静态方法

- Promise.all(promiseArray)
  • 作用:
    • 接受一个数组作为参数,将执行结果以数组形式顺序返回
    • 并发执行数组中的promise对象
  • 特性:
    • 接受一个数组作为参数,数组元素可以是普通值,也可以是promise对象
    • 执行结果以数组形式返回,数组中元素跟传入的promiseArray一一对应
    • 如果传入的数组中元素是普通值,直接原样将对应值放入结果数组中
    • 如果传入的数组中元素是promise对象,将并发执行对应的Promise对象,并等待执行结束,返回结果 ```javascript const promise1 = new Promise((resolve, reject) => { setTimeout(() => { resolve("p1"); }, 2000); }); const promise2 = new Promise((resolve, reject) => { setTimeout(() => { resolve("p2"); }, 1000); });

const promiseAll = Promise.all([1, 2, promise1, 3, 4, promise2, 5]); promiseAll.then((res) => { //并发执行promise //执行结果与传入的数组一一对应 //会等待所有任务执行完毕之后统一返回结果 console.log(res); //[1,2,"p1",3,4,"p2",5] }); ```

  • 如果传入的数组中某一项执行失败,那么Promise将会执行失败 ```javascript const promise1 = new Promise((resolve, reject) => { setTimeout(() => { resolve("p1"); }, 2000); }); const promise2 = new Promise((resolve, reject) => { setTimeout(() => { reject('我这该死的温柔,居然执行失败了') }, 1000); });

const promiseAll = Promise.all([1, 2, promise1, 3, 4, promise2, 5]); promiseAll.then((res) => { // 任何一个任务执行失败 ,整个promise将执行失败 console.log(res); }).catch(e => { //任何一个任务失败,将导致整个Promise执行失败 console.log('fail',e) });

```

- Promise.allSettled(promiseArray)

非正式版,目前处于stage4阶段,尚未完全被浏览器支持

  • 作用:
    • 同Promise.all
  • 特性:
    • 等待数组中所有任务执行完毕,返回一个数组
    • 无论成功还是失败,都会有返回结果
    • 其它同Promise.all ```javascript const promise1 = new Promise((resolve, reject) => { setTimeout(() => { resolve("p1"); }, 2000); }); const promise2 = new Promise((resolve, reject) => { setTimeout(() => { reject("我这该死的温柔,居然执行失败了"); }, 1000); });

const promiseAll = Promise.allSettled([1, 2, promise1, 3, 4, promise2, 5]); promiseAll .then((res) => { /** Promise.allSettled执行结果 [ { status: 'fulfilled', value: 1 }, { status: 'fulfilled', value: 2 }, { status: 'fulfilled', value: 'p1' }, { status: 'fulfilled', value: 3 }, { status: 'fulfilled', value: 4 }, { status: 'rejected', reason: '我这该死的温柔,居然执行失败了' }, { status: 'fulfilled', value: 5 } ] */ console.log(res); }) .catch((e) => { console.log("fail", e); });

```

- Promise.race(promiseArray)
  • 作用
    • 接受一个数组, 并发执行数组中的任务
    • 谁执行块,就返回谁的结果,无论成功还是失败
    • 一般用来做网络超时功能 ```javascript const promise1 = new Promise((resolve, reject) => { setTimeout(() => { resolve("p1"); }, 2000); }); const promise2 = new Promise((resolve, reject) => { setTimeout(() => { resolve("p2"); }, 1000); }); const promise3 = new Promise((resolve, reject) => { // 假设500毫秒后网络超时 setTimeout(() => { reject("超时了"); }, 500); });

const promiseRace = Promise.race([promise1, promise2, promise3]); promiseRace .then((res) => { console.log(res); }) .catch((e) => { // 谁执行块,就返回谁 console.log("fail", e); });

```

- Promise.reject(reason)
  • 作用:
    • 返回一个状态为失败的Promise,并将失败信息传递给对应的处理方法 ```javascript Promise.reject("rejected") .then((res) => { console.log('value', res); }) .catch((reason) => { // reason rejected console.log('reason', reason); });

```

- Promise.resolve(value)
  • 作用:
    • 接受一个值,返回一个Promise
  • 特性:
    • 如果value是一个普通值,则将普通值作为新Promise的resolve结果
    • 如果value是一个Promise,则将value原样返回 ```javascript Promise.resolve(100).then((res) => { console.log(res); //100 });

const promise = new Promise((resolve, reject) => { reject(200); }); promise .then((res) => { console.log(res); //200 });

```

总结

至此,Promise的用法就总结完啦,感谢大家的阅读,希望对大家有所帮助。有什么想法快去评论区说出来吧,我们一起探讨,共同进步。
在了解完Promise使用方法之后,下一篇文章,我将通过手写源码的方式,进一步讲解Promise的核心原理。

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值