lihuamao33

导航

 

什么是Promise?

Promise是异步编程的一种解决方案。

什么时候会来处理异步事件,一种较常见场景就是网络请求。

当进行封装一个网络请求的函数时,因为不能立即拿到结果所以不能像3+4=7一样将结果返回,所以往往我们会传入另一个函数,在数据请求成功时将数据通过传入的函数回调出去,如果只是一个简单的网络请求,这种方案不会给我们带来很大的麻烦。

但是当网络请求非常复杂时,就会出现回调地狱。

例如这个场景

我们需要通过一个url1从服务器加载一个数据data1,data1中包含了下一个请求的url2;

我们需要通过data1取出url2,从服务器加载数据data2,data2中包含了下一个请求的url2;

我们需要通过data2取出url3,从服务器加载数据data3,data3中包含了下一个请求的url4;

发送网络请求url4,获取最终的数据data4

使用ajax实现:
$ajax('url1',function (data1) {
  $ajax(data1['url2'], function(data2) {
    $ajax(data2['url3'], function(data3) {
      $ajax(data3['url4'], function(data4) {
        console.log(data4);
      })
    })
  })
})

上面的解决方法比较难看且不易维护,若两个请求之间隔了很长其他的代码会更乱,而Promise可以以一种非常优雅的方式来解决这个问题。😊😊😊

//resolve,reject本身也是函数,同时也是参数
//当执行resolve时去执行then
new Promise((resolve, reject) => {
  setTimeout(() => {
    resolve()
  },1000)
}).then(() => {
    
})

什么情况下用promise?

一般情况下是有异步操作时,使用Promise对这个异步操作进行封装。

new Promise((resolve, reject) => {
        setTimeout(() => {
            /* resolve('hello world') */
            reject('error message')
        }, 1000)
    }).then(data => {
        console.log(data);
    }).catch(err => {
        console.log(err);
    })

Promise的三种状态

首先当我们开发中有异步操作时,就可以给异步操作包装一个Promise,异步操作之后有三种状态。

pending:等待状态,比如正在进行网络请求,或者定时器没有到时间;

fulfill:满足状态,当我们主动回调了resolve时,就处于该状态,并且会回调.then();

reject:拒绝状态,当我们主动回调了reject时,就处于该状态,并且会回调.catch();

Promise的链式调用

在看Promise的流程图时,无论是then还是catch都可以返回一个Promise对象,所以代码可以进行链式调用。

直接通过Promise包装新数据,将Promise对象返回:

Promise.resovle():将数据包装成Promise对象,并且在内部回调resolve()函数;

Promise.reject():将数据包装成Promise对象,并且在内部回调reject()函数。

链式调用简写

如果希望数据直接包装成Promise.resolve,那么在then中可以直接返回数据。

new Promise((resolve, reject) => {
  setTimeout(function () {
      resolve('Hello world')
  }, 1000)
}).then(data => {
    console.log(data); //Hello world
    return data + '111'
}).then(data => {
    console.log(data); //Hello world111
    return data + '222'
}).then(data => {
    console.log(data); //Hello world111222
    return Promise.reject(data + 'error')
}).then(data => {
    console.log(data); //这部分不会输出,这部分代码不会执行
    return data + '333'
}).catch(data => {
    console.log(data); // Hello world111222error
    return data + '444'
}).then(data => {
    console.log(data);//Hello world111222error444
})

Promise的all方法使用

当同时有两个请求且两个请求都获取后才能进行后续功能。

//使用ajax方法解决
//请求一:
//写两个变量用来判断哪个请求先请求到
let isResult1 = false
let isResult2 = false
$ajax({
  url: '',
  success: function() {
    console.log('结果一')
      isResult1 = true
      handleResult()
  }
})
//请求二:
$ajax({
  url: '',
  success: function() {
    console.log('结果二')
      isResult2 = true
      handleResult()
  }
})
function handleResult() {
    //判断当两个变量都为true时进行后续功能开发
    if (isResult1 && isResult2) {
        
    }
}

使用Promise .all,用于某一个需求需要两次请求

Promise.all([
  new Promise((resolve, reject) => {
    $ajax({
      url: 'url1',
      success: functionn(data) {
        resolve(data)
      }
    })
  }),
    new Promise((resolve, reject) => {
        $ajax({
          url: 'url2',
          success: functionn(data) {
            resolve(data)
          }
        })
      }).then(result => {
          results[0]
          results[1]
      })

new Promise((resolve, reject) => {
    setTimeout(() => {
        resolve({name: 'why', age: 18})
    }, 2000)
}),
new Promise((resolve, reject) => {
    setTimeout(() => {
        resolve({name: 'why', age: 19})
    }, 1000)
})
]).then(results => {
    console.log(results)
})

(如有错误请指正)

posted on 2022-08-01 15:53  lihuamao33  阅读(18)  评论(0编辑  收藏  举报