理解JS中的Promise

  通常JS代码是单线程的、按顺序执行的。当遇到网络数据传递、文件读写等耗时操作时,JS可以不必要等待生成结果,而是启用一个异步操作,继续执行后续的代码。 当耗时操作结束后,再回调其结果。例如:

  console.log("coding beginning !!")
  setTimeout(() => {
      console.log(" a delay operation");
  }, 1000);
  console.log("coding ending")

代码的执行结果

  coding beginning !!
  coding ending
  a delay operation
                

  上述运行结果,首先执行第一条语句,第条语句是一个异步操作,耗时1秒钟。JS解释器执行到这儿时不会等到这条语句执行完后再执行第三条 语句,而是并行的执行第三条语句。等到第二条耗时操作结束后,再回调结果,在本例中就是执行箭头函数()=>console.log(" a delay operation")。

Promise

实际上Promse的规范是异步执行的,Promise是一个异步操作。Promise构造函数接受一个函数作为参数,该函数的两个参数分别是resolve 和 reject。

  // 创建未完成的Promise对象
  const promise = new Promise(function(resolve,reject){
      // ...耗时的操作
      if (/*成功条件*/){
          resolve( "200 OK")
      }else{
          reject("fail");
      }
  }).then(function resolve(sucess){
        
  }).catch(function reject(fail){
        
  });
  // ... 接下来的操作

Promise执行一个耗时操作,这个操作有两个函数分别是resolve和reject。因为这个操作耗时比较长,JS解释器不会阻塞在此处,而是执行接下来的 操作,异步地执行。当解释器等到Promise操作完成时,根据结果判断,成功就调用then的resolve函数,失败就调用catch的reject函数。

下面对Promse操作举例:

  function test(resolve, reject) {
      var timeOut = Math.random() * 2;
      console.log('set timeout to: ' + timeOut + ' seconds.');
      setTimeout(function () {
          if (timeOut < 1) {
              console.log('call resolve()...');
              resolve('200 OK');  //成功时的回调函数
          }else {
              console.log('call reject()...');
              reject('timeout in ' + timeOut + ' seconds.'); //失败时的回调函数
          }
      }, timeOut * 1000);
  }
  var promise = new Promise(test).then(function resolve(success){
      //成功时的回调函数体
      console.log(success);
  }).catch(function reject(fail){
      //失败时的回调函数体
      console.log(fail);
  })

上述代码利用Promise模拟一个异步操作,如果延迟时间在1秒内回调then里的resolve函数,如果延迟时间大于1秒,回调catch里的reject函数。上述 的test、resolve、reject函数都可以用匿名函数或箭头函数取代。

 var promise = new Promise((resovle,reject)=>{
      console.log('set timeout to: ' + timeOut + ' seconds.');
      setTimeout(function () {
          if (timeOut < 1) {
              console.log('call resolve()...');
              resolve('200 OK');  //成功时的回调函数
          }else {
              console.log('call reject()...');
              reject('timeout in ' + timeOut + ' seconds.'); //失败时的回调函数
          }
      }, timeOut * 1000);
  }).then((success)=>{
      //成功时的回调函数体
      console.log(success);
  }).catch((fail)=>{
      //失败时的回调函数体
      console.log(fail);
  })

Promise的几种状态

一个promise有三种状态,未开始执行前它的promise状态是pending状态,在异步执行过程中,如果结果是调用了函数参数中的第一个函数,那么它 的promise状态就是fulfilled状态,如果处理结果是调用了函数参数中的第二个函数,那么它的promise状态就是rejected状态。

  var p = new Promise((resolve,reject)=>{
      if (...){
          resolve("success")  //假如最终结果如果调用了resolve函数,p的promise状态是fulfilled,而promise的结果是"success"
      }else{
          reject("fail") //假如最终结果如果调用了resolve函数,p的promise状态是rejected,而promise的结果是"fail"
      }
  })
  p.then(rs=>console.log(rs));  //success  p的promise状体是fulfilled的,就执行本句。rs就是promise的结果
  .catch(err=>console.log(err)); //fail p的promise状体是rejected的,就执行本句。rs就是promise的结果

Promise的静态方法all

多个promise如果其结果状态同为fulfilled,由其组成的promise的状体就是fulfilled,否则是rejected

  var p1 = new Promise((resolve,reject)=>{
      resolve("ok");
  })
  var p2 = new Promise((resolve,reject)=>{
      reject("fail");
  })
  var p = Promise.all([p1,p2]).then(rs=>console.log(rs)).catch(rs=>console.log(rs)); 
  //fail

Promise的静态方法any

多个promise如果其中一个最先结果状态为fulfilled,则返回fulfilled状态,否则返回rejected状态

  const pErr = new Promise((resolve, reject) => {
      reject("总是失败");
    });
    
    const pSlow = new Promise((resolve, reject) => {
      setTimeout(resolve, 500, "最终完成");
    });
    
    const pFast = new Promise((resolve, reject) => {
      setTimeout(resolve, 100, "很快完成");
    });
    
    Promise.any([pErr, pSlow, pFast]).then((value) => {
      console.log(value);
    })
    //"很快完成"

Promise的静态方法race

多个promise最先生成的结果状态就是返回的状态。

  const pSlow = new Promise((resolve, reject) => {
      setTimeout(resolve, 500, "最终完成");
  });
  
  const pFastError = new Promise((resolve, reject) => {
      setTimeout(reject, 100, "很快玩完");
  });
  Promise.race([pSlow, pFastError]).then((value) => {
      console.log(value);
  })
  //"很快玩完"

文章同时发表在:码农编程网 欢迎访问

本节重点

  • 理解JS中的异步操作;
  • Promise是一个异步操作,Promise对象在成功时回调then中的函数,而失败时调用catch中的函数。
  • 了解Promise的all方法,any方法和race方法

posted on 2023-05-24 17:11  崎岖行者  阅读(73)  评论(0编辑  收藏  举报

导航