在上一篇文章中,我们对于promise有了初步的认识,我们了解到promise是new出来的对象,有三个对应pedding,fulfilled,rejected的状态,在初始化时,拥有status和value和初始化参数executor,executor需要传入resolve和reject函数作为参数。
在本节我们继续来探索promise的原理,在了解基本的promse构造后,我们来对then方法进一步介绍,我们知道then是用来处理resolve和reject函数的回调。那么首先我们来定义then方法.
1、then方法需要两个参数,其中onFulfilled代表resolve成功的回调,onRejected代表reject失败的回调。
then(onFulfilled,onRejected){}
2、我们知道promise的状态是不可逆的,在状态发生改变后,即不可再次更改,只有状态为FULFILLED才会调用onFulfilled,状态为REJECTED调用onRejected
then(onFulfilled,onRejected){
if(this.status == Promise.FULFILLED){
onFulfilled(this.value)
}
if(this.status == Promise.REJECTED){
onRejected(this.value)
}
}
3,then方法的每个方法都不是必须的,所以我们要处理当没有传递参数时,应该设置默认值
then(onFulfilled,onRejected){
if(typeof onFulfilled !=='function'){
onFulfilled = value => value;
}
if(typeof onRejected !=='function'){
onRejected = value => value;
}
if(this.status == Promise.FULFILLED){
onFulfilled(this.value)
}
if(this.status == Promise.REJECTED){
onRejected(this.value)
}
}
4,在执行then方法时,我们要考虑到传递的函数发生异常的情况,如果函数发生异常,我们应该让它进行错误异常处理,统一交给onRejected来处理错误
then(onFulfilled,onRejected){
if(typeof onFulfilled !=='function'){
onFulfilled = value => value;
}
if(typeof onRejected !=='function'){
onRejected = value => value;
}
if(this.status == Promise.FULFILLED){
try{
onFulfilled(this.value)
}catch(error){
onRejected(error)
}
}
if(this.status == Promise.REJECTED){
try{
onRejected(this.value)
}catch(error){
onRejected(error)
}
}
}
5,但是现在我们自己封装的promise有个小问题,我们知道原生的promise中then方法都是异步执行,在一个同步任务执行之后再调用,而我们的现在的情况则是同步调用,因此我们要使用setTimeout来将onFulfilled和onRejected来做异步宏任务执行。
if(this.status=Promise.FULFILLED){
setTimeout(()=>{
try{
onFulfilled(this.value)
}catch(error){
onRejected(error)
}
})
}
if(this.status=Promise.REJECTED){
setTimeout(()=>{
try{onRejected(this.value)}catch(error){onRejected(error)}
})
}
现在then方法中,可以处理status为FULFILLED和REJECTED的情况,但是不能处理为pedding的情况,接下来进行几处修改。
6,在构造函数中,添加callbacks来保存pending状态时处理函数,当状态改变时循环调用
constructor(executor) {
...
this.callbacks = [];
...
}
7,在then方法中,当status等于pending的情况时,将待执行函数存放到callbacks数组中。
then(onFulfilled,onRejected){
...
if(this.status==Promise.PENDING){
this.callbacks.push({
onFulfilled:value=>{
try {
onFulfilled(value);
} catch (error) {
onRejected(error);
}
}
onRejected: value => {
try {
onRejected(value);
} catch (error) {
onRejected(error);
}
}
})
}
...
}
8,调用then方法后返回的是一个新的Promise实例 所有需要我们用Promise再包一层
if(this.status=Promise.FULFILLED){
return newPromise = New Promise((resolve, reject) => {
setTimeout(()=>{
try{
let x = onFulfilled(this.value)
resolve(x)
}catch(error){
let y = onRejected(error)
reject(y)
}
})
})
}
9,完整的部分是这样的
then(onFulfilled,onRejected){
if(typeof onFulfilled !=='function'){
onFulfilled = value => value;
}
if(typeof onRejected !=='function'){
onRejected = value => value;
}
if(this.status == Promise.FULFILLED){
return newPromise = New Promise((resolve, reject) => {
setTimeout(()=>{
try{
let x = onFulfilled(this.value)
resolve(x)
}catch(error){
let y = onRejected(error)
reject(y)
}
})
})
}
if(this.status == Promise.REJECTED){
return newPromise = New Promise((resolve, reject) => {
setTimeout(()=>{
try{
let x = onRejected(this.value)
resolve(x)
}catch(error){
let y = onRejected(error)
reject(y)
}
})
})
}
if(this.status==Promise.PENDING){
return newPromise = New Promise((resolve, reject) => {
this.callbacks.push({
onFulfilled:value=>{
try {
onFulfilled(value);
} catch (error) {
onRejected(error);
}
}
onRejected: value => {
try {
onRejected(value);
} catch (error) {
onRejected(error);
}
}
})
})
}
}
到此,promise的then方法的基本实现就结束了