【问题标题】:Does the for loop block when the iteration invokes an async function without await keyword? (the invoked async function has the await keyword)当迭代调用没有 await 关键字的异步函数时,for 循环是否会阻塞? (调用的 async 函数有 await 关键字)
【发布时间】:2022-02-17 16:47:47
【问题描述】:

在下面的伪代码中,当for循环执行每次迭代时,那么for循环会在每次迭代时阻塞等待异步fetch的响应(因为awaitmyasyncfn内使用?还是我需要使用await 关键字,如下面的评论所示?

async myasyncfn(url){
return await fetch(url..).response;
}

for each url in url_array:
   myasyncfn(url);    #await myasyncfn(url)

【问题讨论】:

  • 不,它没有。
  • 说在第 1 次迭代中,当调用 myasyncfn 时,myasyncfn 中有 await - 这不足以阻止 for 循环吗?
  • 不,不是……

标签: javascript asynchronous async-await


【解决方案1】:

在继续循环之前不会等待async 函数完成;从这个意义上说,它阻塞。但是,这仅仅意味着它会快速连续地遍历所有 URL,触发许多 fetch 请求,然后这些请求将在后台并行运行。一旦循环完成触发这些,您的线程就会被解除阻塞。

举例说明:

async function foo(i) {
    await new Promise(resolve => setTimeout(resolve, 5000));
    console.log('Completed', i);
}

for (let i = 0; i < 10; i++) {
    foo(i);
    console.log('Fired', i);
}

console.log('Done firing all async functions, unblocking...');

【讨论】:

  • 说在第 1 次迭代中,当调用 myasyncfn 时,myasyncfn 中有 await - 这是否不足以阻止 fetch 操作和 for 循环?
  • 它会“阻止”myasyncfn 的完成,但它会在后台暂停直到fetch 完成并且不会阻止主线程。
  • 你的答案是正确的,但从技术上讲,在第一次迭代时,当主线程调用 foo 时,那么在函数内,为什么主线程不阻塞 foo 内的 await 迭代?这个概念叫什么,所以我可以阅读它?
  • await 明确地从主线程中删除该函数。它暂停了函数的执行,因为该函数需要等待其他事情并且现在无法继续,并允许其他事情在主线程上发生。要搜索的关键字:generators。将await 读作“这个函数现在需要等待一些结果,因此可以暂时从(阻塞)执行中删除。”
  • (在 Javascript 中 await 通常只是回调函数的语法糖,因此生成器暂停通常并不真正适用,但从概念上讲它确实适用,其他语言以这种方式实现。)
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 2020-03-23
  • 1970-01-01
  • 1970-01-01
  • 2019-07-17
  • 2021-08-30
  • 2016-06-09
  • 2019-07-24
相关资源
最近更新 更多