JavaScript 中 foreach 的回調函數並行執行探究

在我們正常的表裏數組操作中有兩大類方式:一種是通過for/while的方式進行遍歷,另一種就是通過Array內置的方法,比如 foreach,map,every,some,reduce等。

這些操作處理同步的回調函數都是串行執行的,以下選取 for 和 foreach 做示例:

// 定義數組
const arr = [1,'a',2,'b',3,'c']
// 定義同步回調函數
const foo = i => {
  if(typeof i === 'number'){
    for(let i =0;i<1000000000;i++){
    }
    console.log(i)
  }else{
    console.log(i)
  }
  return true;
}
  • for 函數執行結果:
// 定義for函數遍歷
function a() {
  for (var i = 0; i < arr.length; i++) {
    foo(arr[i])
  }
}
a() // 輸出:1 a 2 b 3 c
  • foreach 執行結果:
// map,some,every,reduce 執行結果都一樣,請自行驗證
function e() {
  arr.map((a) => foo(a))
}
e()  // 輸出:1 a 2 b 3 c

結論:對於同步任務兩者的表現都是串行執行

js 對於異步任務都是交給瀏覽器並行執行的,但是最新的 ES 語法中有 async/await 語法糖,它可以將異步任務當作同步任務的形式來執行。

那對於 async/await 這種的異步任務,這兩種遍歷方式是如何執行的呢?請看以下示例:

// 定義數組
const arr = [1,'a',2,'b',3,'c']
// 定義異步任務
const foo = i => {
  return new Promise((resolve, reject) => {
    if(typeof i === 'number'){
      setTimeout(() => {
        console.log(i)
        resolve(i)
      }, 500)
    }else{
      setTimeout(() => {
        console.log(i)
        resolve(i)
      }, 1000)
    }
  })
}
  • for 函數執行結果:
async function a() {
  for (var i = 0; i < arr.length; i++) {
    await foo(arr[i])
  }
}
a() // 輸出:1 a 2 b 3 c
  • foreach 執行結果:
// map,some,every,reduce 執行結果都一樣,請自行驗證
function e() {
  arr.forEach(async (a) => await foo(a))
}
e() // 輸出:1 2 3 a b c

結論:由此可見 for 這類遍歷對於 async/await 任務依然是串行執行,但是 forEach 這類遍歷對於 async/await 是並行執行的

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章