2012-01-31 10 views
12

Così Sto usando questo in IE8:IE8 per ... in enumeratore

var hi=["hi", "lo", "foo", "bar"]; 
for(i in hi){console.log(i)}; 
//WTF is that indexOf i value? 
LOG: 0 
LOG: 1 
LOG: 2 
LOG: 3 
LOG: indexOf 
undefined 

in cromo e altri, mi limiterò a ottenere 0-3, nessuna misteriosa cosa "indexOf". Perché e qual è la soluzione?

risposta

23

Non utilizzare for...in per gli array. È preferibile utilizzare il ciclo tradizionale for in questo caso.

La ragione è che for...in guarda la matrice come un oggetto, e quindi immobili come indexOf o length possono essere inclusi nel ciclo. Il normale ciclo for riguarda solo i tasti numerici, quindi questo problema viene evitato.

Su una nota a fianco, le proprietà indesiderate possono essere visualizzate quando si itera su oggetti semplici e (come altri hanno notato, le proprietà che si aggiungono al prototipo dell'oggetto verranno visualizzate). È possibile ottenere intorno a questo scrivendo i tuoi for...in loop in questo modo:

var obj = { ... }; 
for (var prop in obj) { 
    if (obj.hasOwnProperty(prop)) { 
    var item = obj[prop]; 
    ... 
    } 
} 

essere chiaro però: si ancora Non si deve usare questo metodo su array.

+0

grazie! Ninja ... – randomor

7

Si sta utilizzando il tipo sbagliato di ciclo per un array - for ... in ... saranno anche includere qualsiasi enumerabili proprietà dell'oggetto, che nel tuo caso include il metodo .indexOf().

Utilizzare questo invece:

var i, n = hi.length; 
for (i = 0; i < n; ++i) { 
    console.log(i, hi[i]); 
} 

Chrome e altri browser fino a data implementare ECMAScript 5, e correttamente segnano tutti i metodi built-in come non enumerabili proprietà.

+1

Ha, ci battiamo ancora! – benekastah

+0

'indexOf' non è un metodo array in IE8, viene aggiunto dall'utente, motivo per cui viene visualizzato – Esailija

+0

IE8 non ha' indexOf() '? Wow... – Alnitak

4

Ciò accade perché uno script incluso nella pagina sta aggiungendo il metodo indexOf a Array.prototype. Ciò significa che tutti gli array ereditano un metodo indexOf, che è buono, poiché significa che è possibile utilizzare tale metodo anche in IE8.

Ma, dal momento che non v'è alcun modo per segnare una proprietà come non enumerabile in IE8, si finisce per vedere ogni volta che si enumerare su tutte le proprietà della matrice, che è quello che si fa in un for-in ciclo continuo. Probabilmente hai preferito un ciclo for.