代码之家  ›  专栏  ›  技术社区  ›  Uğur Kaya

编写异步/等待版本的承诺

  •  2
  • Uğur Kaya  · 技术社区  · 5 年前

    下面的代码按预期每秒记录一次“hello world”。

    function moveOneStep() {
      return new Promise((res, rej) => {
        setTimeout(() => {
          res(console.log('Hello world!'))
        }, 1000)
      })  
    }
    
    async function main() {
      await moveOneStep();
      await moveOneStep();
      await moveOneStep();
      await moveOneStep();
    }
    

    考虑到 return 安的价值 async 函数与返回的内容相对应 resolve 函数在承诺中,为什么下面的代码不输出相同的结果,而是同时记录所有的“hello world:

    async function moveOneStepAsync() {
      setTimeout(() => {
        return console.log('Hello world!');
      }, 1000);
    }
    
    async function main() {
      await moveOneStepAsync();
      await moveOneStepAsync();
      await moveOneStepAsync();
      await moveOneStepAsync();
    }
    
    2 回复  |  直到 5 年前
        1
  •  6
  •   Danil Gudz    5 年前

    那是因为 setTimeout 不履行承诺 await 它在你 main 功能。setTimeout本身同步执行。它向事件循环中添加了作为参数传递的回调,以便在提到的时间内执行。

    同样,在这段代码中,回调的返回意味着没有任何内容,因为回调将在1秒内运行,返回的值将不复存在。

    async 关键字告诉您函数返回Promise,并且 等待 里面有代码。因为代码中没有等待,所以看起来

    function moveOneStepAsync() {
      setTimeout(() => {
        return console.log('Hello world!');
      }, 1000);
      return Promise.resolve();
    }
    

    所以你的 等待 总的来说,将等待一个事件循环勾选转到下一个“步骤”

    阅读有关setTimeout、事件循环以及wait期望更深入地了解它的内容。

        2
  •  1
  •   Jonas Wilms    5 年前

    你不 return 函数的任何内容,都返回到内部setTimeout函数,这与该值无关。打电话 setTimeout 不返回承诺,而是立即返回计时器。因此 moveOneStepAsync 调用立即执行,计时器被设置,一秒钟后触发。