es6 Promise

Posted cavalary

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了es6 Promise相关的知识,希望对你有一定的参考价值。

ES6的Promise是一个构造函数,Promise 对象用于一个异步操作的最终完成(或失败)及其结果值的表示,也就是处理异步操作的,异步请求成功,处理成功的操作,异步请求失败停止后续操作。自身有all、reject、resolve方法,原型上有catch、then方法。

一般可以表示为如下,resolve,reject,分别表示异步操作执行成功后的回调函数和异步操作执行失败后的回调函数。

  new Promise(resolve,reject){
        if(/*success*/){
            sesolve();
        }else{ // fail
            reject();
        }
    }

Promise有三种状态:

1.Pending初始状态,也称为未定状态,就是初始化Promise时,调用executor执行器函数后的状态。

2.Fullfiled完成状态,意味着异步操作成功。

3.rejected失败状态,意味着异步操作失败。

如果异步操作成功,则可以调用resolve()来将该实例的状态置为fulfilled,即已完成的,如果一旦失败,可以调用reject()来将该实例的状态置为rejected,即失败的。

 

    function promise(){
        return new Promise(function(resolve,reject){
        //异步操作
        setTimeout(function(){
            console.log(‘完成‘);
            resolve(‘执行‘);
        },1000)
        })
    }
    promise();

这里的promise()函数其实就是 return出来的Promise对象,下面对Promise上的方法then运用下

Promise.prototype.then()

    promise().then(function(data){
        console.log(data);
    }).then(function(data){
        console.log(data); //这里没有返回值所以执行undefined
    })

技术分享图片

运行结果是1秒后出来完成和执行,这里拿到了resolve里面的参数,显然是把原来的回调写法分离出来,在异步操作执行完后,用链式调用的方式执行回调函数,Promise的优势在于,可以在then方法中继续写Promise对象并返回,然后继续调用then来进行回调操作。

Promise不仅简化了异步操作的写法,也让维护状态、传递状态的方式来使得回调函数能够及时调用。

    promise().then(function(data){
        console.log(data);
        return new Promise(function(resolve,reject){
        //异步操作
        setTimeout(function(){
            console.log(‘完成2‘);
            resolve(‘执行2‘);
        },1000)
        })
    }).then(function(data){
        console.log(data);
        return new Promise(function(resolve,reject){
        //异步操作
        setTimeout(function(){
            console.log(‘完成3‘);
            resolve(‘执行3‘);
        },1000)
        })
    }).then(function(data){
        console.log(data);
    })

执行结果

技术分享图片

每个1秒输出异步回调的内容,在then方法中也可以直接return数据,而不是Promise对象,在后面的then中就可以接收到数据了,比如

    promise().then(function(data){
        console.log(data);
        return new Promise(function(resolve,reject){
        //异步操作
        setTimeout(function(){
            console.log(‘完成2‘);
            resolve(‘执行2‘);
        },1000)
        })
    }).then(function(data){
        console.log(data);
        return new Promise(function(resolve,reject){
        //异步操作
        setTimeout(function(){
            console.log(‘完成3‘);
            resolve(‘执行3‘);
        },1000)
        })
    }).then(function(data){
        console.log(data);
        return ‘数据‘
    }).then(function(data){
        console.log(data)
    })

 

技术分享图片

Promise.prototype.catch()

除了then方法,Promise对象上还有catch方法,catch()方法和then()方法一样,都会返回一个新的Promise对象,它主要用于捕获异步操作时出现的异常。因此,我们通常省略then()方法的第二个参数,把错误处理控制权转交给其后面的catch()函数,如下:

    function promise(){
        return new Promise(function(resolve,reject){
        //异步操作
        setTimeout(function(){
            reject(‘reject‘);
        },1000)
        })
    }
    promise().then(function(data){
        console.log(data); //这里是fullfiled状态,不会触发
    }).catch(function(err){
        console.log(‘出错‘+err); //reject
    })

如果resolve执行时出现错误,那会把错误的信息传递到catch原因里如下:

    function promise(){
        return new Promise(function(resolve,reject){
        //异步操作
        setTimeout(function(){
            resolve(‘成功‘);
            reject(‘reject‘);
        },1000)
        })
    }
    promise().then(function(data){
        console.log(aa); //这里是fullfiled状态,不会触发
    }).catch(function(err){
        console.log(‘出错‘+err); //reject
    })

技术分享图片

这里的aa的确没有定义,catch执行了then的错误信息,如果换成data,执行成功,就不会继续执行reject,因为当前状态没有出错。

Promise.all()

all方法提供了并行执行异步操作的能力,并且在所有异步操作执行完后才执行回调,Promise.all()接收一个数组参数,它通常用来处理一些并发的异步操作,即它们的结果互不干扰,但是又需要异步执行。它最终只有两种状态:成功或者失败。

    Promise.all([new Promise(function(resolve,reject){
        setTimeout(function(){
            console.log(‘异步1‘)
            resolve(‘成功1‘);
        },1000)
        }), new Promise(function(resolve,reject){
        setTimeout(function(){
            console.log(‘异步2‘)
            resolve(‘成功2‘);
        },1000)
        }), new Promise(function(resolve,reject){
        setTimeout(function(){
            console.log(‘异步3‘)
            resolve(‘成功3‘);
        },1000)
        })]).then(function(results){
        console.log(results);
    })

技术分享图片

all会把所有异步操作的结果放进一个数组中传给then,三个异步操作是并行执行的。

Promise.race()

Promise.race()和Promise.all()类似,都接收一个可以迭代的参数,不同之处是Promise.race()的状态变化不是全部受参数内的状态影响,一旦参数内有一个值的状态发生的改变,那么该Promise的状态就是改变的状态,就是它的字面意思谁跑的快,以谁为准执行回调,如下我们把异步时间有所改变来看下效果:

 

    Promise.race([new Promise(function(resolve,reject){
        setTimeout(function(){
            console.log(‘异步1‘);
            resolve(‘成功1‘);
        },1000)
        }), new Promise(function(resolve,reject){
        setTimeout(function(){
            console.log(‘异步2‘);
            resolve(‘成功2‘);
        },500) //这里改为500ms
        }), new Promise(function(resolve,reject){
        setTimeout(function(){
            console.log(‘异步3‘);
            resolve(‘成功3‘);
        },1000)
        })]).then(function(results){
        console.log(results);
    })

 执行结果:

 技术分享图片

这三个异步操作同样是并行执行的,但是异步2明显快于其他两个异步操作。

 

以上是关于es6 Promise的主要内容,如果未能解决你的问题,请参考以下文章

es6-promise源代码重点难点分析

如何在 ES6 中将回调代码转换为 Promise [重复]

ES6 promise

ES6 promise对象

es6从零学习:promise

ES6的Promise