Promise与await / async

原文参考链接

  1. 先来看一下 callback 的问题场景,一般加载一个Script是异步加载,我们想知道加载是否成功,很通常的做法是给一个callback,代码如下:

    function loadScript(src, callback) {
      let script = document.createElement('script');
      script.src = src;
    
      script.onload = () => callback(null, script);
      script.onerror = () => callback(new Error(`Script load error for ${src}`));
    
      document.head.append(script);
    }
    // 等同于
    loadScript('/my/script.js', function(error, script) {
      if (error) {
        // handle error
      } else {
        // script loaded successfully
      }
    });
    

    假设我们需要顺序加载三个script,即第一个成功后加载第二个,然后再加载第三个,那么上面的代码就是嵌套内再添加嵌套。这样显然是不太好的一种处理方式。

    loadScript('/my/script1.js', function(error, script) {
      if (error) {
        // handle error
      } else {
        loadScript('/my/script2.js', function(error, script) {
            if (error) {
              // handle error
            } else {
              loadScript('/my/script3.js', function(error, script) {
                  if (error) {
                    // handle error
                  } else {
                    // script loaded successfully
                  }
                });
            }
        });
      }
    });
    

    callback 使用的过程中只能有一个回掉,且回掉内的功能也必须是明确的。

  2. Promise链式处理
    promise接受两个参数,并且可以设置一段时间后进行。但是只会触发一次reject/resolve

    let promise = new Promise(function(resolve, reject){
        alert(resolve);
        alert(reject);
    
        setTimeout(() => resolve("finished!"),1000);
    });
    
    let promise = new Promise(function(resolve, reject) {
      resolve("done");
    
      reject(new Error("…")); // ignored
      setTimeout(() => resolve("…")); // ignored
    });
    

    promise还提供了.then .catch方法用于处理结果后的执行,并且可以多次调用。

    promise.then(
      function(result) { /* handle a successful result */ },
      function(error) { /* handle an error */ }
    );
    
    /* case 1 */
    let promise = new Promise(function(resolve, reject) {
      setTimeout(() => resolve("done!"), 1000);
    });
    
    /* resolve runs the first function in .then */
    promise.then(
      result => alert(result), // shows "done!" after 1 second
      error => alert(error) // doesn't run
    );
    
    /* case 2 */
    let promise = new Promise(function(resolve, reject) {
      setTimeout(() => reject(new Error("Whoops!")), 1000);
    });
    
    /* reject runs the second function in .then */
    promise.then(
      result => alert(result), // doesn't run
      error => alert(error) // shows "Error: Whoops!" after 1 second
    );
    
    /* case 3 */
    let promise = new Promise(resolve => {
      setTimeout(() => resolve("done!"), 1000);
    });
    
    promise.then(alert); // shows "done!" after 1 second
    

    promise.then的处理结果是异步的,且取决于Promise构造函数内的处理结果。

    • Promise.resolve: makes a resolved promise with the given value,
    let promise = Promise.resolve(value);
    等价于
    let promise = new Promise(resolve => resolve(value));
    
    • Promise.reject:makes a rejected promise with the given error
    let promise = Promise.reject(error);
    等价于
    let promise = new Promise((resolve, reject) => reject(error));
    
    • Promise.all: waits for all promises to resolve and returns an array of their results. If any of the given promises rejects, then it becomes the error of Promise.all, and all other results are ignored.
    let promise = Promise.all(iterable);
    Promise.all([
      new Promise((resolve, reject) => setTimeout(() =>     resolve(1), 3000)), /* 1 */
      new Promise((resolve, reject) => setTimeout(() =>     resolve(2), 2000)), /* 2 */
      new Promise((resolve, reject) => setTimeout(() =>     resolve(3), 1000))  /* 3 */
    ]).then(alert); 
    /* Promise.all下面的3秒后结算,然后结果是一个数组[1, 2, 3] */
    
    • Promise.race: waits for the first promise to settle, and its result/error becomes the outcome。
  3. await 与 async
    await只能在async里面使用。
    async始终返回一个promise。

你可能感兴趣的:(Promise与await / async)