[英]difference between for loop and for-in loop in javascript
我發現javascript中的for循環和for-in循環之間有區別。
當我定義一個新數組時:
var a=new Array();
然后例如但不連續地添加一些值:
a[0]=0;a[1]=1;a[4]=4;
當我使用for(i=0;i<5;i++)
獲取值並使用alert顯示它時,它與使用for(i in a)
。
前一個將顯示索引2,3中的元素,該元素顯示“未定義”,而for-in將僅顯示索引0,1和4。有人可以告訴我為什么嗎?
For循環遍歷它們,直到i達到5,因此i = 0、1、2、3、4、5並遍歷所有。 但是,使用for ... in循環僅迭代其屬性,而不是0到5,而是您定義的0,1,4。
從MDN :
注意: for..in不應用於遍歷索引順序很重要的Array。
數組索引只是具有整數名稱的可枚舉屬性,其他方面與常規Object屬性相同。 無法保證for ... in將以任何特定順序返回索引,並且將返回所有可枚舉的屬性,包括具有非整數名稱的屬性和被繼承的屬性。
因為迭代的順序取決於實現,所以在數組上進行迭代可能不會以一致的順序訪問元素。 因此,在訪問順序很重要的數組上進行迭代時,最好使用帶有數字索引的for循環(或Array.forEach或for ... of循環)。
for (... in ...)
通常用於遍歷對象的屬性(這是javaScript用於關聯數組的屬性),而典型的for
循環用於順序數組。
在您的示例中,您實際上是在用鍵0、1和4創建一個關聯數組。如果要使用真正的javaScript數組,則可以使用a.push(0)
, a.push(1)
等。 。為了添加值, 順序地 ,在陣列上的端部。
對於順序數組,語法for (var i = 0; i < arr.length; i++)
使i
計數從0到1小於數組的長度。 這將使i
一一等於數組中的每個索引,從而允許您訪問該數組中的每個元素。
但是,對於關聯數組,鍵是非順序鍵,因此使變量計數“比數組長度小0到1”將不會產生期望的結果。 在您的示例中,由於您手動創建的鍵恰好是0、1和4(幾乎是連續的),因此已接近正常工作。
如果您想要一個帶有非順序鍵的數組(例如“ 0”,“ 1”,“ 4”等“非連續”鍵),則應該使用對象而不是數組,例如
var obj = {};
obj[0] = 0;
obj[1] = 1;
obj[4] = 4;
然后使用for (... in ...)
循環將是正確的語法。
for-in循環枚舉變量的可枚舉屬性。 對於您的數組,將“ 0”,“ 1”和“ 4”作為可枚舉屬性添加到數組中。 因此,for-in循環在“ i”中僅獲得0、1和4。
for循環適用於i = 0至5。因此,您也嘗試訪問2和3處的值,這些值顯然是未定義的。
語法
for (var k in obj)
實際上是一個for-each循環。 它遍歷對象的屬性。 您應該熟悉JavaScript對象。 對象是鍵到值的映射。
因此,for-each循環對對象非常有用。 但是,在遍歷數組時,最好使用常規的for循環。
這是在對象的屬性上使用的for-each循環的示例: http : //jsfiddle.net/nbtLpw0z/ 。
我使用的是for-in循環,因為它是一種較短的形式,但是有時您可能希望控制迭代變量。 例如,如果要遍歷偶數索引,則需要使用常規的for循環:
for (var i = 0; i < myarray.length; i+=1) {...}
例如,如果要向后迭代,則同樣適用:
for (var i = myarray.length-1; i >= 0; i--) {...}
當然,對於對象,for-in循環允許您在迭代變量中獲取屬性名稱。
var obj = {year: 2014, city: "Surat"}
for (var propn in obj) alert(propn + " = " + obj[propn]);
在您的示例中,我將使用for-in,因為您正在執行簡單的迭代。 而且我認為在未優化的Javascript編譯器/解釋器中,for-in循環會更快,因為變量增量是在內部完成的。
對於初學者來說for in
Array上使用for in
循環是沒有意義的for in
因為JavaScript中的數組只能具有有序的數字索引。 因此,您可以在0
到array.length - 1
之間的任何索引處訪問數組,如果您想使用for in循環遍歷數組,您當然可以,但是,常規的for循環更合適。
如果您沒有訂購數字索引,則使用for in
循環。 JavaScript對象實際上是一個有序哈希表。 您可以使用in
操作符訪問JavaScript對象的鍵,該操作符返回對象的鍵,並通過訪問該鍵的對象來獲取值。
例如:
var obj = {
hello: "world",
world: "hello"
};
常規的for循環不起作用,因此您無需使用for in
循環。
for(var i in obj) console.log(obj[i]);
對象也不會返回足夠准確的length屬性以迭代整個對象,因此for in
循環是絕對必要的。
還要注意,通過不按下一個空閑元素的存在順序為數組分配值,將自動在您跳過的元素中放置undefined
。
在您的示例中,數組如下所示:
[0, 1, undefined × 2, 4]
for-each
環被推薦用於遍歷對象屬性,而for
循環被推薦用於陣列。 您可以使用push()
獲得相同的結果。
var a = []; //recommended way of declaring arrays over `new Arrays()` a.push(0); a.push(1); a.push(4); //usual for-loop for (var i = 0; a.length > i; i++) //recommended console.log('a[', i, ']=', a[i]); console.log('---------------------'); // for-each loop for (var k in a) //not recommended console.log('a[', k, ']=', a[k]); console.log('---------------------');
Open console...
var person = { 'name': 'Adam' }; for (var k in person) console.log('person.' + k, '=', person[k]); console.log('----------------------'); person.age = 26; //new property for (var k in person) console.log('person.' + k, '=', person[k]); console.log('----------------------'); person['gender'] = 'Male'; //again a new property for (var k in person) console.log('person.' + k, '=', person[k]); console.log('----------------------'); person.name = 'Will'; //updating property for (var k in person) console.log('person.' + k, '=', person[k]); console.log('----------------------');
Open console...
在幕后,for-in循環不過是for循環。 For(i in x)分解為-
for(i=0;i<x.length;i++) {
if(x[i] != undefined)
console.log(x[i]);
}
我已經閱讀並聽到了正常的for循環: for(var i = 0; i < arr.length; i++)
更快。 但是我會說for of
使用:
var arr = [1,2,3], obj = {x: 1, y:2};
for(var value of arr) console.log(value) // 1, 2, 3
for(var key in obj) console.log(key) // x, y
for(var key of Object.keys(obj)) console.log(key) // x, y
您可以使用Object.keys(obj)
將對象的鍵轉換為數組,並在其上調用Array.prototype
方法
您的“ for”循環從0-4開始查看數組索引的所有值,因為這正是您要執行的操作。 因此,它先查看a [0]並找到一個值,然后找到a [1](相同的交易),然后轉到a [2]並意識到您從未為a [2]初始化一個值,因此未定義。 a [3]也是一樣,最后a [4]具有一個值,以便找到它。
這種“ for”循環的類型將檢查每個索引是否已定義。
“ for ... in ...”循環將僅檢查初始化值。 您的數組具有3個已初始化的值,因此它將檢查這些值。 它將按照索引的順序向您顯示,但是索引實際上並不會影響它的外觀。 因此,如果將“ a [1]”更改為“ a [3]”,將“ a [4]”更改為“ a [10]”,則將“。”使用時仍會得到完全相同的答案。 。in ...”循環中。
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.