(javascript)为什么await在forEach中不生效?

转载:为啥await在forEach中不生效?-腾讯云开发者社区-腾讯云 (tencent.com)

两天要写循环遍历请求接口,于是就在forEach中用到了await,但是根本不是我想要的啊!

于是各种查,各种搜,终于有点明白了。先看段代码:

function test(){
  let arr =[3,2,1]
  arr.forEach(async item=>{
    const res = await fetch(item)    
    console.log("end")
  })
}

function fetch(x){
  return new Promise((resolve,reject)=>{
    setTimeout(()=>{
      revolve(x)
    }, 500*x)
  })
}

test();

期望打印出来顺序是:

3
2
1
end

然而打印顺序却是:

end
1
2
3

原因是forEach只支持同步代码

Pollyfill版本的forEach,简化以后类似于下面的伪代码:

while(index < arr.length){
  callback(item, index)
}

解决办法

方法一:Promise.all

async function test(){
  let arr = [3,2,1]
  await Promise.all(arr.map(async item=>{
    const res = await fetch(item);
    console.log(res)
  }))
  console.log("end")
}

async函数肯定会返回一个Promise对象,map返回一个存放Promise的数组。但是这样并不能保证fetch是按顺序完成的,如果想按顺序,请用下面的方法。

方法二:for ... of

async function test(){
  let arr =[3,2,1];
  for(const item of arr){
    const res = await fetch(item);
    console.log (res)
  }
  console.log("end")
}

function fetch(x){
  return new Promise((resolve,reject)=>{
    setTimeout(()=>{
      resolve(x)
    }, 1500*x)
  })
}

test();

因为for... of和forEach内部的机制不同,forEach是直接调用回调函数,for...of 是通过迭代器的方式去遍历的:

async function test(){
  let arr = [3,2,1];
  const iterator = arr[Symbol.iterator]()
  let res = iterator.next()
  while(!res.done){
    const value = res.value;
    const res1 = await fetch(value);
    console.log(res1);
    res.iterator.next();
  }
  console.log("end")
}

以上代码等价于for...of

参考文章:https://yuchengkai.cn/blog/2019-04-01.html#%E6%80%8E%E4%B9%88%E8%A7%A3%E5%86%B3%EF%BC%9F

评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值