• Promise then中回调为什么是异步执行?Promise执行机制问题


    今天发现一个问题,看下方代码

     let p = new Promise(function(resolve, reject) {
        resolve(1)
        console.log('2222');
     });
    p.then(res => {
        console.log('1111');
    })

    输出结果是2222 1111,而自己想的是1111 2222,带着问题查询之后发现.

    原来then后边跟的都是异步执行..学习到了.

    此链接是各位大佬的回答https://www.zhihu.com/question/57071244

    用网上学习ES5实现的Promise ,输出结果和自己想的一样,原因可以去上方地址找到.

    下方是ES5实现的promise

    function Promise(callback) {
      var self = this;
      self.status = 'PENDING'; // Promise当前的状态
      self.data = undefined; // Promise的值
      self.onResolvedCallback = []; // Promise resolve时的回调函数集
      self.onRejectedCallback = []; // Promise reject时的回调函数集
      callback(resolve, reject); // 执行executor并传入相应的参数
    
      function resolve(value) {
        if (self.status == 'PENDING') {
          self.status == 'FULFILLED';
          self.data = value;
          // 依次执行成功之后的函数栈
          for (var i = 0; i < self.onResolvedCallback.length; i++) {
            self.onResolvedCallback[i](value);
          }
        }
      }
    
      function reject(error) {
        if (self.status === 'PENDING') {
          self.status = 'REJECTED';
          self.data = error;
          // 依次执行失败之后的函数栈
          for (var i = 0; i < self.onRejectedCallback.length; i++) {
            self.onRejectedCallback[i](error);
          }
        }
      }
    }
    
    Promise.prototype.then = function(onResolved, onRejected) {
      var self = this;
      var promise2;
    
      // 根据标准,如果then的参数不是function,则我们需要忽略它,此处以如下方式处理
      onResolved = typeof onResolved === 'function' ? onResolved : function(value) {};
      onRejected = typeof onRejected === 'function' ? onRejected : function(reason) {};
    
      if (self.status === 'FULFILLED') {
        // 如果promise1(此处即为this/self)的状态已经确定并且是resolved,我们调用onResolved
        // 因为考虑到有可能throw,所以我们将其包在try/catch块里
        return (promise2 = new Promise(function(resolve, reject) {
          try {
            var x = onResolved(self.data);
            if (x instanceof Promise) {
              // 如果onResolved的返回值是一个Promise对象,直接取它的结果做为promise2的结果
              x.then(resolve, reject);
            }
            resolve(x); // 否则,以它的返回值做为promise2的结果
          } catch (e) {
            reject(e); // 如果出错,以捕获到的错误做为promise2的结果
          }
        }));
      }
    
      // 此处与前一个if块的逻辑几乎相同,区别在于所调用的是onRejected函数,就不再做过多解释
      if (self.status === 'REJECTED') {
        return (promise2 = new Promise(function(resolve, reject) {
          try {
            var x = onRejected(self.data);
            if (x instanceof Promise) {
              x.then(resolve, reject);
            }
          } catch (e) {
            reject(e);
          }
        }));
      }
    
      if (self.status === 'PENDING') {
        // 如果当前的Promise还处于pending状态,我们并不能确定调用onResolved还是onRejected,
        // 只能等到Promise的状态确定后,才能确实如何处理。
        // 所以我们需要把我们的**两种情况**的处理逻辑做为callback放入promise1(此处即this/self)的回调数组里
        // 逻辑本身跟第一个if块内的几乎一致,此处不做过多解释
        return (promise2 = new Promise(function(resolve, reject) {
          self.onResolvedCallback.push(function(value) {
            try {
              var x = onResolved(self.data);
              if (x instanceof Promise) {
                x.then(resolve, reject);
              }
              resolve(x); // 否则,以它的返回值做为promise2的结果
            } catch (e) {
              reject(e);
            }
          });
    
          self.onRejectedCallback.push(function(reason) {
            try {
              var x = onRejected(self.data);
              if (x instanceof Promise) {
                x.then(resolve, reject);
              }
            } catch (e) {
              reject(e);
            }
          });
        }));
      }
    };
    
    // 为了下文方便,我们顺便实现一个catch方法
    Promise.prototype.catch = function(onRejected) {
      return this.then(null, onRejected);
    };
    

      

  • 相关阅读:
    64位win2008下IIS未开启32位支持导致DLL无法加载问题
    多控制器传递不同类型实体类到共用视图方案
    敏捷开发学习笔记——产品经理
    一些Razor语法
    敏捷开发学习笔记——用户故事与多职能团队
    UM九图
    Linq的分页
    easyUI datagrid 前端真分页
    C#项目的生成事件及批处理文件
    子类复制父类的值
  • 原文地址:https://www.cnblogs.com/chengfeng6/p/10823064.html
Copyright © 2020-2023  润新知