不可不知的promise

176 阅读2分钟

第一部分:promise用法

关键点

先上一波关键点:

  1. Promise 承诺 就是一个类型
  2. new Promise时需要传递一个executor执行器(同步执行的)
  3. executor中有两个参数 resolve 成功 reject 失败
  4. 每个promise的实例上都有一个then方法,then方法有2个函数,成功和失败
  5. promise有3个状态pending,成功 resolve,失败 reject
  6. promise使用时,需要new Promise()
  7. then方法执行完会判断返回的结果,如果时promise会把这个promise执行,会取到他的结果
  8. 每次调用then方法后会再返回一个新的promise,并不是this
  9. promise的链式调用,解决了回调嵌套的问题
  10. .then().then().then(),值的穿透,直接传到下面
  11. then中返回promise会把promise的结果作为下一个then的参数;then返回的是一个普通值,把这个普通值做为下一次then的成功的结果
  12. return Promise.reject('失败了')
  13. es2018草案,即es9中增加finally,不管成功还是失败都会执行
  14. 多个异步并发执行,需要在同一时刻内获取最终结果,Promise.all,全部成功才成功,有一个失败就失败
  15. Promise.race([p1, p2, p3])里面哪个结果获得的快,就返回那个结果,不管结果本身是成功状态还是失败状态

代码对比

异步写法:

let fs = require('fs');
let school = [];

fs.readFile('./name.txt','utf8',function(err,data){
    school.push(data);
    fs.readFile('./age.txt','utf8',function(err,data){
        school.push(data);
        console.log(school)
    }
}

promise写法:

let fs = require('fs');
let school = [];

function read(url,encoding){
    return new Promise(function(resolve,reject){
        fs.readFile(url,encoding,function(err,data){
            if(err)reject(eff)
            resolve(data)
        })
    })
}

read('name.txt','utf8').then(function(data){
        return read(data,'utf8');
    }).then(function(data){
        return read(data,'utf8')
    }).catch(function(err){
        console.log('catch',err)
    })
})

第二部分:promise实现

开发promise需要遵从promise A+规范,网址:promisesaplus.com/

最最简单的promise实现:

function Promise(executor) {
  let self = this;
  // 保存成功的值和失败的原因
  self.value = undefined;
  self.reason = undefined;
  // 保存一下当前这个promise的状态(promise有三个状态)
  self.status = 'pending';
  function resolve(value) {
    if (self.status === 'pending') {
      self.value = value;
      self.status = 'resolved';
    }
  }
  function reject(reason) {
    if (self.status === 'pending') {
      self.reason = reason;
      self.status = 'rejected';
    }
  }
  executor(resolve, reject);
  // executor是立即执行的
}
// then方法中需要传递两个参数 分别是成功的回调和失败的回调
Promise.prototype.then = function (onFulfilled,onRejected) {
  let self = this;
  if(self.status === 'resolved'){
    onFulfilled(self.value);
  }
  if (self.status === 'rejected') {
    onRejected(self.reason);
  }
}
module.exports = Promise

测试

npm i promises-aplus-tests -g
安装promises-aplus-tests,这个包可以用来测试我们写的promise是否符号a+规范