js中4種遍歷語法比較

前言:本文主要比較for、for-in、forEach和for-of的異同以及優缺點。html

for

for循環是最原始最易理解的循環遍歷方式數組

for(var index = 0;index < arr.length;index++){
    console.log(arr[index])
}
  • 使用continue和break能夠跳出本次循環和退出循環

forEach

上述for循環的寫法比較繁瑣,所以數組提供了內置的forEach方法數據結構

arr.forEach((item, index) => {
    consoel.log(item)
})

注意函數

  • forEach的寫法帶來了便利,但因爲其每次循環其實是一個回調函數,所以在函數內部沒法用continue和break(用於循環)跳出循環
  • 能夠用return跳出本次循環(至關於continue),而要退出循環只能拋出錯誤
var arr = [1,2,3]
arr.forEach((item) => {
    if (item === 2){
        return;// 跳出本次循環
    }
    console.log(item)
}
// 輸出1,3
try {
    arr.forEach((item) => {
    if (item === 2){
        throw new Error() // 退出循環
    }
    console.log(item)
})
} catch(e) {}
// 輸出1

for-in

for-in主要爲遍歷對象而設計,也能夠遍歷數組的鍵名。
for-in有幾個特色,一般狀況下被認爲是缺點:性能

  • 數組的鍵名是數字,但for-in循環是以字符串做爲鍵名
var arr = ['a']
for(var item in arr){
    console.log(item, typeof item)
}
// 1, string
  • for-in循環沒法保證對數組的遍歷順序(遍歷對象時也沒法保證),因爲數組是以鍵值對的形式存儲(詳情可見js的數組在內存中是如何存儲的),所以其沒法保證遍歷順序的緣由與遍歷對象一致,詳情可見js中對象的輸出順序
  • for-in會遍歷全部可枚舉屬性(包括原型鏈上的屬性),且因爲js中數組是以鍵值對的形式存儲,所以數組的非索引屬性也會被遍歷
var arr = ['a', 'b']
Array.prototype.protoName = '原型屬性'
arr.name = '非索引屬性'
for(var item in arr){
    console.log(arr[item])
}
// a,b,'非索引屬性','原型屬性'

能夠發現,for-in不只遍歷了原型鏈上的屬性,新增的非索引屬性name頁被遍歷,所以for-in不適合遍歷數組。(因爲length等屬性是不可枚舉屬性,所以沒有被遍歷)prototype

  • for-in循環性能較差
    因爲每次循環,for-in不只會搜索實例屬性,還會搜索原型屬性,所以相比於其餘循環方式,for-in的速度較慢。
var arr = new Array(10000)
for(var i=0;i< 10000;i++){
    arr[i]=i
}
var length = arr.length
console.time('for')
for (var index=0; index< length; index++){
    // 
}
console.timeEnd('for')
console.time('for-in')
for(var index in arr){
    //
}
console.timeEnd('for-in')
// for:0.2839ms
// for-in: 1.1479ms

所以,除非須要迭代一個屬性數量未知的對象,不然並不適合用for-in循環。
以上for-in的特性,在日常開發中共基本上都是缺點,但有一種可能算是優勢的特性:for-in只會遍歷數組中存在的實體設計

var arr = new Array(3)
arr[2] = 'hello world'
var length = arr.length
for (var index=0; index< length; index++){
    console.log(arr[index])
}
// undefined,undefined, 'hello world'
for(var index in arr){
    console.log(arr[index])
}
// 'hello world'

能夠看到for-in會忽略數組中爲定義的部分,能夠用於遍歷長度很大的稀疏數組。)code

for-of

相比於以上幾點,for-of幾乎結合了它們的全部優勢:htm

  • 有着for-in同樣簡單的語法,但沒有for-in的缺點
  • 不一樣於forEach,for-of可使用break和continue跳出循環
  • 提供了遍歷全部數據結構的統一操做接口
  • 不只支持對象和數組的遍歷,for-of支持一切可迭代對象的遍歷,包括類數組、字符串的遍歷;它將字符串視爲一系列Unicode字符來遍歷。

但須要注意,普通對象不是可迭代對象,不能用for-of遍歷。想要迭代一個對象,能夠用for-in,也能夠將對象使用Map數據結構對象

相關文章
相關標籤/搜索