es6异步操作Promise

责编:menVScode 2018-02-25 17:31 阅读(523)

        Promise 是 ES6 中新增的异步编程解决方案,体现在代码中它是一个对象,可以通过 Promise 构造函数来实例化。

        new Promise(cb) 是有3种状态的:Pending(进行中)、Resolved(已完成)、Rejected(已失败)。它的状态完全由异步操作的结果决定的,且状态一旦确认是不可以被改变的。

const imgs = [
    'http://img13.360buyimg.com/n7/jfs/t16144/347/1402836971/215478/4effd883/5a547208N4e8e6102.jpg',
    'http://img10.360buyimg.com/n7/jfs/t12994/338/733574425/319777/f266f597/5a128bebN55293392.jpg',
    'http://img14.360buyimg.com/n7/jfs/t14272/313/469442847/128364/78c17964/5a2e3251N0c98ecbf.jpg'
]
const p = new Promise(function(resolve,reject){
    // resolve: 异步操作执行成功时的回调函数
    // reject: 异步操作执行失败时的回调函数
    const img = new Image();
    img.src = imgs[0];
    img.onload = function(){
        resolve(this)
    }
    img.onerror = function(){
        reject(new Error('图片加载失败'))
    }
})

// then: 异步操作执行完成后,要执行的函数
// 一般不建议在then中写第二个参数捕获异常,而是使用catch来捕获异常。
p.then(
    function(img){ // 异步操作执行成功时的回调函数
        console.log(img)
        document.body.appendChild(img)
    },
    function(err){ // 异步操作执行失败时的回调函数
        console.log(err)
    })

        一般不建议在then中写第二个参数捕获异常,而是使用catch来捕获异常。

// then: 异步操作执行完成后,要执行的函数
p.then(function(img){ // 异步操作执行成功时的回调函数
    console.log(img)
    document.body.appendChild(img)
}).catch(function(err){
    console.log(err)
})

        Promise.all():可以将多个 Promise 实例包装成一个新的 Promise 实例。

        当所有的 Promise 实例的状态都变成了 resolved,此时返回值组成一个数组,传递给 then 中的 resolve 函数。

const imgs = [
    'http://img13.360buyimg.com/n7/jfs/t16144/347/1402836971/215478/4effd883/5a547208N4e8e6102.jpg',
    'http://img10.360buyimg.com/n7/jfs/t12994/338/733574425/319777/f266f597/5a128bebN55293392.jpg',
    'http://img14.360buyimg.com/n7/jfs/t14272/313/469442847/128364/78c17964/5a2e3251N0c98ecbf.jpg'
]

function loadImg(url){
    const p = new Promise(function(resolve,reject){
        const img = new Image();
        img.src = url;
        img.onload = function(){
            resolve(this)
        }
        img.onerror = function(){
            reject(new Error('图片加载失败'))
        }
    })
    return p;
}

let allDone = Promise.all([ loadImg(imgs[0]),loadImg(imgs[1]),loadImg(imgs[2]) ]);
allDone.then(function(imgs){
    console.log(imgs); // [img, img, img]
    console.log(imgs[2]); // <img src='http://img14.360buyimg.com/..3251N0c98ecbf.jpg' />
    imgs.forEach(function(item,i){
        document.body.appendChild(item)
    })
})

        只要其中有一个被 rejected,Promise.all() 的状态就会变成 rejected,此时第一个被 rejected 的实例的返回值,会传递给p的回调函数。

let allDone = Promise.all([ loadImg(imgs[0]),loadImg(imgs[1]),loadImg(imgs['']) ]);
allDone.then(function(imgs){
    imgs.forEach(function(item,i){
        document.body.appendChild(item)
    })
}).catch(function(err){
    console.log(err); // Error: 图片加载失败
})

        Promise.resolve():将一个对象转换称 Promise 对象,他的使用方式有三种。

        【1】参数是一个Promise实例:

        如果参数是Promise实例,那么Promise.resolve将不做任何修改、原封不动地返回这个实例。

// 如果参数是Promise实例,那么Promise.resolve将不做任何修改、原封不动地返回这个实例。
Promise.resolve( loadImg(imgs[0]) ).then(function(data){
    console.log(data)
})

        【2】参数是一个 thenable 对象

        thenable对象指的是具有then方法的对象,比如下面这个对象。

let thenable = {
  then: function(resolve, reject) {
    resolve(42);
  }
};

        Promise.resolve方法会将这个对象转为Promise对象,然后就立即执行thenable对象的then方法。

let thenable = {
  then: function(resolve, reject) {
    resolve(42);
  }
};

let p1 = Promise.resolve(thenable);
p1.then(function(value) {
  console.log(value); 
})
Promise.resolve({
    then(resolve,reject){
        const img = new Image();
        img.src = imgs[1];
        img.onload = function(){
            resolve(this);
        }
    }
}).then(function(img){
    document.body.appendChild(img)
})

        【3】参数是基本数据类型。

        当传入字符串类型的数据,会返回一个新的新的Promise对象,并且返回Promise对象的状态是resolved,而且menvscode这个参数会变成resolve()函数的参数。

Promise.resolve('menvscode').then(function(data){
    console.log(data); // menvscode
})

        【4】不带有任何参数

        Promise.resolve方法允许调用时不带参数,直接返回一个Resolved状态的Promise对象

const p = Promise.resolve()
console.log(p); // Promise {[[PromiseStatus]]: "resolved", [[PromiseValue]]: undefined}
标签: Promise es6
前端交流群: MVC前端网(menvscode.com)-qq交流群:551903636

邮箱快速注册

忘记密码