【问题标题】:What exactly happens when awaiting a promise in JavaScript?在 JavaScript 中等待 promise 时究竟会发生什么?
【发布时间】:2019-10-12 21:32:57
【问题描述】:

我似乎在文档或相关资源的任何地方都找不到的一点是,当 JS 遇到 await 关键字时,关于调用函数和事件循环的过程是什么。

specs 状态如下:

await 表达式导致异步函数执行暂停,直到 Promise 被解决,即被履行或拒绝,并在履行后恢复异步函数的执行。恢复时,await 表达式的值是已履行的 Promise 的值。

这一切都说得通,但暂停的真正含义是什么?函数是否立即返回给调用者,然后当等待的 promise 解决时,它和异步方法的其余部分被添加到微任务队列中进行处理?我知道async/await 是 Promise API 的语法糖,所以我假设这就是发生的事情,但我想确保我真的理解当达到 await 时发生的“魔法” .

根据我的阅读,这似乎是在 C# 中完成的,但我不确定它是如何转换为 JS 的。

【问题讨论】:

    标签: javascript promise async-await


    【解决方案1】:

    果然如你所说,将函数的其余部分放入一个微任务Q中,并返回主函数。

    然后当 promise 解决时,它会执行异步部分。

    帮助我理解的是将async/await转换成promise语法,然后就明白了。

    例如:

    async function doSomthing() {
      someSync();
    
      const result1 = await someAsync();
      const result2 = await someAsync2();
    
      return result1 + result2;
    }
    

    “转换”为:

    function doSomthing() {
      someSync();
    
      return someAsync().then(result1 => {
        return someAsync2().then(result2 => {
          return result1 + result2;
        });
      });
    }
    

    您可以看到doSomthing 立即返回承诺。

    【讨论】:

    • 非常感谢! “返回主函数”是什么意思?
    • 在我的示例中 doSomthing 立即返回一个承诺,没有任何异步。
    • 谢谢!现在,如果您在第一次 await 之前在函数中执行了代码,那么它不会在 await 关键字被命中之前返回,对吧?
    • 如果在第一个await之前有同步的代码,它会在第一个异步操作排队之前执行
    • 我已经更新了我的答案,someSync函数会在someAsync之前执行
    【解决方案2】:

    await/async 表示我们同步执行代码。它将按照在 async 函数中调用 await 函数的顺序。 例如:它将逐行处理执行,就像等待它从等待返回响应一样,然后继续执行。

     `function doubleAfter2Seconds(x) {
        return new Promise(resolve => {
          setTimeout(() => {
            resolve(x * 2);
          }, 2000);
        });
      }
    
      async function addAsync(x) {
         console.log("Here I am before first await"); 
        const a = await doubleAfter2Seconds(10);
        console.log("A ouput is ",a);
        const b = await doubleAfter2Seconds(20);
        console.log("B ouput is ",b);
        const c = await doubleAfter2Seconds(30);
        console.log("C ouput is ",c);
        return x + a + b + c;
      }
    
    
      addAsync(10).then((sum) => {
        console.log(sum);
      });`
    

    以上代码将输出如下结果:

    希望这有助于理解 async/await

    【讨论】:

      猜你喜欢
      • 2015-12-25
      • 2015-10-23
      • 2011-01-18
      • 2012-01-15
      • 1970-01-01
      • 2014-08-20
      • 1970-01-01
      • 2016-03-01
      • 2019-07-29
      相关资源
      最近更新 更多