for語句在js剛出來的時候,就已經存在了,而map和forEach這兩個方法都是ES5時出來的,前者為語句,後者為方法。map和forEach這兩個方法,都需要傳遞參數,並且該參數是一個回調函數,所以,單純的從性能上講,map和forEach方法是遠遠落後for語句的。

既然map和forEach性能沒有for好,那麼為什麼在ES5時,設計出這兩個方法?

答案是作用域保存數據的問題。

看下面的代碼:

<input type="button" value="a" />

<input type="button" value="b" />

<input type="button" value="c" />

<script>

var arr=document.getElementsByTagName("input"), i=0, len=arr.length;

for( ; i<len; i++ ){

arr[i].onclick = function(){

alert( i );

}

}

</script>

你覺得上面的代碼,當點擊b那個按鈕時,輸出的是什麼?

你可能覺得輸出的是1啊,很簡單啊,但答案實際上是2,原因是i是全局變數,根據代碼的執行順序,當點擊按鈕的時候,for循環早就執行完了,那麼i就是2。

如果程序這樣寫呢?

Array.from(arr).forEach( (btn, ind)=>{

btn.onclick = ()=>{

alert( ind );

}

} );

點擊哪一個按鈕,就會對應輸出這個按鈕的下標。因為forEach方法裡面,參數部分的那個回調函數,數組成員有多少個,它就執行多少次,函數是存在作用域的,btn和ind都是這個函數的局部變數,所以循環時,彼此沒有任何影響。

所以,很多時候,用forEach來實現循環,會更方便一點,但性能確實比for語句差很多。

map方法和forEach方法類似,都是對數組進行循環,數組中每一個成員,都被其回調函數處理一次。區別在於map有返回值,而forEach沒有返回值。

var arr = [1,2,3,4,5];

var r = arr.map( (v, i)=>{

return v*2;

} );

console.log(r); // [2,4,6,8,10]

如果在上文代碼中,將map換為forEach,那麼r的結果就是undefined,其他沒區別,所以性能上map稍落後於forEach。

上圖為我推薦給大家的一本說,裡面有好多性能方面的解答。

推薦閱讀:

相关文章