Promise的使用

Promise本意承诺,是一个承诺将来会执行的对象

基本用法是reject后的东西,一定会进入then中的第二个回调,如果then中没有写第二个回调,则进入catch ,resolve的东西,一定会进入then的第一个回调,肯定不会进入catch, 网络异常(比如断网),会直接进入catch而不会进入then的第二个回调

let p = new Promise(function(resolve,reject){
console.log('立即执行');
    setTimeout(function(){
        resolve('成功');
    },100);
});

p.then(function(data){
console.log(data);
},function(err){
console.log(err);
})

创建Promise对象时,executor执行器会同步执行(在Promise构造函数返回Promise对象之前就会被执行),executor是一个函数,函数内部通常调用用来执行一些异步操作,操作完成后,调用resolve触发promise的成功状态,或者调用reject触发promise的失败状态。

 then 用来注册Promise状态确定后的回调;then的参数有:处理成功返回结果的函数,处理错误结果的函数;then方法返回一个Promise,因此可以继续调用then,即实例化后的Promise对象可以进行链式调用

//读取文件1.txt ,1.txt中存放着文本2.txt,再读取2.txt文件的内容
let fs = require('fs');
function read(path){
return new Promise(function(resolve,reject){
        fs.readFile(path,'utf8',function(err,data){
if(err){
                reject(err);
            }
        resolve(data)
        })
    })
}

read('1.txt').then(data=>{
console.log(data);
//return data;// 如果返回了一个普通值,会将这个值作为下一次then的成功会回调
return read(data);
},err=>{
console.log(err);
}).then(data=>{
console.log('next then :',data);
},err=>{
console.log(err);
})

Promise状态

1pending:默认状态,就是初始化Promise时,调用executor执行器函数后的状态。

2fulfilled:完成状态/成功状态,异步操作调用resolve()后的状态  

3rejected:失败状态,异步操作调用reject()后的状态 

 状态转化:pending ->fulfilled ,pending ->rejected 这个状态转化是单向的,不可逆转的,也就是一旦进入成功就成功了,一旦进入失败就失败了

链式调用返回一个Promise,该Promise的状态主要根据第一个then方法返回的值确定

 1、如果第一个then()方法中返回了一个参数值,那么返回的Promise将会变成接收状态。

 2、如果第一个then()方法中抛出了一个异常,那么返回的Promise将会变成拒绝状态。

 3、如果第一个then()方法调用resolve()方法,那么返回的Promise将会变成接收状态。

 4、如果第一个then()方法调用reject()方法,那么返回的Promise将会变成拒绝状态。

 5、如果第一个then()方法返回了一个未知状态(pending)Promise新实例,那么返回的新        Promise就是未知状态。 

不管第一个then走的成功还是失败,都会将返回值(没有返回值,就返回undefined)作为下一个then的结果 

Promise.all(promises) 

all 接收一个参数,它必须是可以迭代的,比如数组,它通常用来处理一些并发的异步操作, 是多个promise对象的结果集合

 

//Promise.all方法执行后返回的依旧是promise
//它是并发执行的,返回结果按照执行顺序,即ele2是read('2.txt')的返回结果
//all里面的都执行成功了,才表示成功,有一个失败了,就失败
Promise.all([read('1.txt'),read('2.txt')]).then(([ele1,ele2])=>{
console.log(ele1,ele2);
},err=>{
console.log(err);
});

 Promise.race()

Promise.race() all基本相同,race“赛跑的意思,race的状态变化不是全部受参数内的状态影响,一旦参数内有一个值的状态发生的改变,那么该Promise的状态就是改变的状态

// race如果先成功了那就成功了如果先失败了那就失败了
Promise.race([read('1.txt'),read('2.txt')]).then(([ele1,ele2])=>{
   console.log(ele1,ele2);
},err=>{
   console.log(err);
});

Promise.resolve() / Promise.reject()

参数可以是普通值或Promise对象

let p = Promise.resolve([1,2]);
p.then(data=>{
console.log(data);
})
Promise.reject([1,2,3]).then(null,function(err){
console.log('err',err)
}); 
let p2 = Promise.reject(['fail']);
let p3 = Promise.resolve(p2).then(data=>{
console.log('不执行');
},err=>{
console.log('resolve接收rejected状态的promise',err);
});

组合  promise

例如,假设我们需要编程解决如下需求:

  1. 创建 HTTP 请求,等待请求结束并打印出结果;
  2. 再创建两个并行 HTTP 请求;
  3. 等这两个请求结束后,打印出它们的结果
// 第一次调用

const call1Promise = rp('http://example.com/');

 

call1Promise.then(result1 => {

    // 第一个请求完成后会执行

    console.log(result1);

    const call2Promise = rp('http://example.com/');

    const call3Promise = rp('http://example.com/');

 

    return Promise.all([call2Promise, call3Promise]);

}).then(arr => {

    // 两个 promise 都结束后会执行

    console.log(arr[0]);

    console.log(arr[1]);

})

我们开头创建了第一个 HTTP 请求,并且加了个完成时候运行的回调。在这个回调函数里,我们为随后的 HTTP 请求创建了另外两个 promise。这两个 promise 同时执行,我们需要加一个能等它们都完成后才执行的回调函数。因此,我们需要用 Promise.all 将它们组合到同一个 promise 中,它们都结束后这个 promise 才算完成。这个回调返回的是 promise 对象,所以我们要再加一个 then 回调函数来打印结果。

如果我们必须执行更多异步操作,或者加上错误处理,这种方法最后很容易产生一堆乱七八糟的 then, Promise.all 和回调函数。JavaScript ES7 中的 async / await 让多个异步 promise 协同工作起来更容易。

Async 方法

Async 是定义返回 promise 对象函数的快捷方法。

function f() {

    return Promise.resolve('TEST');

}

 

// asyncF 和 f 是等价的

async function asyncF() {

    return 'TEST';

}

Await

每个 async 方法都返回一个 promise 对象。因此,JavaScript 解释器就明白所有 async 方法中的操作都被封装在 promise 里异步执行。所以解释器能够允许它们等待其他 promise 执行完。

await 只能被用在 async 方法中,让我们能同步等待 promise 执行完。如果在 async 函数外使用 promise, 我们仍然需要用 then 回调函数。

解决上面提到的多个异步 promise 协同工作:

// 将解决方法封装到 async 函数中

async function solution() {

  

    // 等待第一个 HTTP 请求并打印出结果

    console.log(await rp('http://example.com/'));

 

  

    // 创建两个 HTTP 请求,不等它们执行完 —— 让他们同时执行

    const call2Promise = rp('http://example.com/');  // Does not wait!

    const call3Promise = rp('http://example.com/');  // Does not wait!

 

    

    // 创建完以后 —— 等待它们都执行完

    const response2 = await call2Promise;

    const response3 = await call3Promise;

 

    console.log(response2);

    console.log(response3);

}

 

 

// 调用这一 async 函数

solution().then(() => console.log('Finished'));

实际上,async / await 在底层转换成了 promise 和 then 回调函数。也就是说,这是使用 promise 的语法糖。每次我们使用 await, 解释器都创建一个 promise 对象,然后把剩下的 async 函数中的操作放到 then 回调函数中。

async function f() {

    console.log('Starting F');

    const result = await rp('http://example.com/');

    console.log(result);

}

 

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值