一、Promise是什么?

promise是对象,它的状态不受外界影响,代表一个异步操作

二、异步的操作由哪些?

  • setTimeout 延时调用,可以让这个时间延迟,然后去触发
  • setInterval 间歇调用,每隔多长时间就执行一次
  • ajax
  • 图片加载
  • 文件操作

    三、promise状态

  1. pending 进行中
  2. fulfilled(resolve) 成功的状态
  3. rejected失败

    四、优缺点

  • 优点:

    1. promise对象,可以将异步操作以同步操作流程表达出来,避免了层层嵌套的回调函数,解决回调地狱的问题,用法上链式调用
  • 缺点:

    1. 1.无法取消promise,一旦新建就会立即执行,无法中途取消<br /> 2.不设置回调函数,promise内部抛出的错误,反应不到外部<br /> 3.pendding状态时,无法得知进展到哪一个阶段

    五、promise的原型对象(实例)

    ```javascript let p1= new Promise() p1.then()//接收成功的回调 p1.then(res(接收成功的信息),error(接收失败的信息)) p1.catch()//接收错误的回调 p1.catch(res(接收成功的信息),error(接收失败的信息)) p1.finally()//无论成功失败,都会触发

  1. <a name="klGf1"></a>
  2. #### 六、promise构造函数上的方法,不能用实例来调用
  3. - Promise.all()
  4. ```javascript
  5. 多个promise实例包装成一个实例,所有的状态都成功才会调用.then,只要由一个不成功就会调用.catch()
  6. Promise.all([axios.get('轮播图'),axios.get('列表')]).then(res=>{
  7. res[0]//轮播图
  8. res[1]//列表
  9. })
  10. -------------------------------------------------------------------------------------------
  11. function water() {
  12. return new Promise((resolve, reject) => {
  13. setTimeout(() => {
  14. resolve("烧水");//成功
  15. }, 1000);
  16. });
  17. }
  18. function cut() {
  19. return new Promise((resolve, reject) => {
  20. setTimeout(() => {
  21. reject("切菜");//错误
  22. }, 1000);
  23. });
  24. }
  25. Promise.all([water(), cut()]).then(res => {
  26. //烧水和切菜的结果都是resolve()成功的时候,Promise.all().then才会执行,有其中一个不成功,不执行
  27. console.log(res);
  28. });
  • promise.race() ```javascript Promise.race([p1,p2,p3])接收的时数组,那个结果获取的快,就返回那个结果,无论结果是成功/失败 使用场景:
  • 多台服务器部署同样的服务端代码,假设要获取商品列表的接口
  • 在race中写上所有服务器中的查询商品列表的接口地址,那个服务器响应快,就从那个服务器拿数据。

  1. function water() {
  2. return new Promise((resolve, reject) => {
  3. setTimeout(() => {
  4. resolve("烧水");
  5. }, 2000);
  6. });
  7. }
  8. function cut() {
  9. return new Promise((resolve, reject) => {
  10. setTimeout(() => {
  11. resolve("切菜");
  12. }, 1000);
  13. });
  14. }
  15. Promise.race([water(), cut()]).then(res => {
  16. //哪一个结果返回的快,就返回那个结果。
  17. console.log(res);['切菜','烧水']
  18. });
  1. - promise.resolve()
  2. - promise.reject()
  3. ```javascript
  4. let p=new Promise((resolve,reject)=>{
  5. // resolve('成功')
  6. reject('失败')
  7. })
  8. console.log(p);// Promise {<rejected>: "失败"}
  9. p.then(res=>{
  10. console.log(res);
  11. }).catch(error=>{
  12. console.log(error);
  13. })
  14. 结论:状态只能从pendding-->成功||pendding-->失败
  15. console.dir(Promise)可以获取到Promise构造函数上的属性和方法
  16. console.log()会在浏览器控制台打印出相关信息

举例:闯关消消乐

  1. <script>
  2. function play(timer, key = 1) {
  3. return new Promise((resolve, reject) => {
  4. setTimeout(() => {
  5. key++; //第二关的要是
  6. resolve('成功的信息');
  7. reject('失败的信息')
  8. }, timer);
  9. });
  10. }
  11. play(1000).then(two => {
  12. console.log('第二关的钥匙',two);
  13. return play(2000, two);//第三关能用,否则接收不到参数
  14. }).then(three=>{
  15. console.log(`第三关的钥匙 ${three}`);
  16. // return play(3000,three)
  17. }).catch(error=>{
  18. console.log(error);//只有状态是失败的时候,才走error
  19. });
  20. </script>

七、简单封装promise

  1. <script>
  2. class MyPromise {
  3. constructor(callback) {
  4. this.status = "pending"; //进行中
  5. this.val = ""; //成功的信息
  6. this.error = ""; //失败的信息
  7. // 成功的函数
  8. const resolve = val => {
  9. if (this.status === "pending") {
  10. this.status = "fulfiled"; //把状态变成成功
  11. this.val = val;
  12. }
  13. };
  14. // 失败的函数
  15. const reject = error => {
  16. if (this.status === "pending") {
  17. this.status = "rejected"; //让状态等于失败
  18. this.error = error;
  19. }
  20. };
  21. callback(resolve, reject); //一进来就触发
  22. }
  23. //成功的回调
  24. then(onResolve, onFail) {
  25. // onResolve(this.val);
  26. if (this.status === "fulfiled") {
  27. onResolve(this.val);
  28. } else {
  29. onFail(this.error);
  30. }
  31. }
  32. }
  33. let p = new MyPromise((resolve, reject) => {
  34. resolve("成功的信息"); //想更换结果,就修改这两个状态
  35. // reject("失败的信息");
  36. }).then(
  37. res => {
  38. console.log(res);
  39. },
  40. error => {
  41. console.log(error);
  42. }
  43. );
  44. </script>
  1. Promise.allSettled
  2. 使用场景:首次进入的时候需要那个能返回数据就用那个,并且要对应证型下的高亮 知道那个是高亮的证型 会把所有场景的字段的接口都掉一次,
  3. let requestlist = []
  4. this.syndromeTypeData.forEach((item) => {
  5. requestlist.push(
  6. this.$Request.drivingSchool({
  7. url: this.$Port.drivingSchool.smallProject,
  8. method: 'post',
  9. data: { schoolId: store.getters['user/userInfo'].schoolId, syndromeType: item.label } //68
  10. })
  11. )
  12. })
  13. // TODO:requestlist接受的是一个数组
  14. Promise.allSettled(requestlist).then((res) => {
  15. res.forEach((item, index) => {
  16. //首次进入的时候需要那个能返回数据就用那个
  17. if (item.value && item.value.data && item.value.data.length) {
  18. this.syndrome = this.syndromeTypeData[index].label
  19. item.value.data.forEach((item) => {
  20. if (item.subject == 'subject2') {
  21. let { isMustFull, ...other } = item
  22. this.subject2Arr.push({
  23. isMustFull: isMustFull ? true : false,
  24. ...other
  25. })
  26. } else {
  27. this.subject2Arr.push({
  28. isMustFull: isMustFull ? true : false,
  29. ...other
  30. })
  31. }
  32. })
  33. //并且要对应证型下的高亮 知道那个是高亮的证型
  34. this.currentIndex = index
  35. }
  36. })
  37. })