这是博主自己对ES6学习中的一些总结,持续更新ing,有错误之处希望大牛们给我指出与提点,小弟在此谢过。
(1)Promise对象是ES6新增对象。可以利用Promise对象进行异步编程。
(2)它包含有3中状态。1.Pending 2.Resolved 3.Rejected,其中状态变化只会从Pending到Resolved或Pending到Rejected,状态变化之后,不可逆不可变!!且在状态改变之后再添加回调函数,获取到的状态还是不变的。
(3)基于Promise状态变化机制,存在一定的缺陷,比如Promise创建之后无法取消,且建立之后无法获知Pending进行的进度。
好了,大概介绍完Promise对象基本内容之后,通过实例来详细解说一下Promise的用法。
var p1 = new Promise(function (resolve, reject) {
console.log("会在创建实例时直接执行,但状态不会改变")
setTimeout(() => reject(new Error('fail')), 3000)
})
var p2 = new Promise(function (resolve, reject) {
setTimeout(() => resolve(p1), 1000)
})
p2.then(result => console.log(result))
.catch(error => console.log(error))
// 会在创建实例时直接执行,但状态不会改变
// Error: fail
以上例子中p1和p2都是Promise对象的实例。
(1)1秒钟之后执行p2的resolve(即状态从Pending变到Resolved),返回的是p1,所以then指向了p1。
(2)p1在3秒之后状态从Pending变到Rejected,因此最后输出结果是catch的错误信息。
其中这里最主要的是then方法和catch方法。
then方法接受两个参数,即是两个回调函数,第一个回调函数是对应Promise实例中Resolved时调用,第二个回调函数时Reject时调用(非必需);
catch方法其实是then的另一种写法,它只有一个参数即对应Promise实例状态变为Rejected时调用的回调函数,当then第一个参数为null时与catch等价;但一般捕捉Rejected状态建议使用catch来操作。
p2.then(result => console.log(result))
.catch(error => console.log(error))
上述写法的好处是catch能够捕捉到then中发生的错误。
catch(error => console.log(error)) == then(null,error => console.log(error)) //等价
有人会想为什么p1还为被调用而p1的打印内容比p2的还早,是因为在p1创建的时候会直接执行,只是状态需要在被调用的时候才会发生改变。
Promise的几个方法。
1.let p = Promise.all([p1,p2,p3])参数一般是一个数组,数组内容一般均为Promise实例,如果不是则先转化为Promise实例再处理。数组内所有实例均返回Resolved则P的状态改为Resolved,否则p的状态为Rejected。
2.let p = Promise.race([p1,p2,p3])参数与all()一致,处理方法也一致,区别在于,race()只要有一个实例状态变化了,p就跟着其状态变化。
3.let p =Promise.resolve(a) 如果a是一个有then方法的对象,那么Promise.resolve会将p转化为Promise对象实例,并把状态改为Resolved,执行then方法。如果a不是上述对象,p依然会转化为Promise对象实例并把状态改为Resolved,但a会成为p.then的回调函数参数。
4.let p = Promise.reject(a),与Promise.resolve状态相反,执行动作一致的方法。
5.done(),为保证promise的错误能够反映出来,done()会在Promise对象回调连的末尾,在报错时执行。
6.finally(),也会在Promise对象回调连最后,与done()的区别是不论是否报错都会执行的回调。