Au cas où « dans » la construction de Javascript itérer la propriété de longueur?
-
22-09-2019 - |
Question
Je fais un bookmarklet, mais je l'ai rencontré un comportement bizarre dans IE8. Le code cause du problème est le suivant:
var els = document.getElementById("my_id").getElementsByTagName("*");
for(var i in els)
{
alert(i+","+els[i])
}
La première chose qui est alerté est « longueur, n ». Ce n'est pas le cas en chrome. Juste IE8
Fait intéressant, il semble se comporter différemment selon que le code va dans la console / barre d'adresse ou la page elle-même.
Est-ce comportement standard?
EDIT:
Pas vers le site que je l'exécute sur soit. Est-il possible que retourne getElementsByTagName
un tableau avec une clé "length"
définie dans IE? Il ne retourne pas certainement un tableau pur.
La solution
Ce que vous obtenez est pas un tableau, il est un nodeList. Voir , cliquez sur le lien "getElementsByTagName ( 'ELEMENT_NAME')"
En outre, for..in est pas destiné à être utilisé pour itérer sur un tableau de toute façon. Utilisez
var item;
for (var idx=0, len=arr.length; idx<len; ++idx) {
item = arr[idx];
// whatever
}
pour l'itération de tableau.
Pour une nodelist, vous pouvez obtenir l'élément avec
list.item(idx); // where list is what you got from getElementsByTagName
si vous voulez le faire "droit".
Autres conseils
Le comportement IE est correcte. Il peut renvoyer toutes sortes de trucs bizarres, depuis itère for .. in
sur tous les noms de membres de l'objet.
getElementsByTagName
renvoie un NodeList
, et les propriétés d'un NodeList
sont spécifiés dans le DOM norme : length
et item(i)
. La plupart des implémentations JavaScript permettront également [i]
.
Par conséquent, vous devez écrire:
var els = document.getElementById("my_id").getElementsByTagName("*");
for (var i = 0;i < els.length;i++)
{
alert(i+","+els.item(i));
}
Ne pas utiliser for..in
pour autre chose que les propriétés d'un énumération objet (sauf si vous aimez les surprises!) Il suffit d'utiliser une simple boucle pour les tableaux et nodelists.
Voici comment j'itérer sur les listes. De cette façon, vous ne serez pas avoir à écrire une ligne supplémentaire dans la boucle, comme var el = els[i]
.
var els = document.getElementById("my_id").getElementsByTagName("*");
for (var i=0, el; el=els[i]; i++) {
// do what you like here
}
Non, sauf si vous définissez votre propre itérateur pour NodeList
s, qui est JavaScript (Mozilla) -seulement. [Voici une implémentation] de celui que j'ai créé pour ma pension js-itérateurs.
Un procédé pour convertir un objet, comme une liste de noeuds, objet arguments, ou objet personnalisé à un tableau de ses membres est souvent utile.
Array.from= function(what){
var L, A= [];
if(!what) what= {};
L= what.length;
if(typeof L== 'number'){
while(L) A[--L]= what[L];
return A;
}
for(var p in what){
if(what.hasOwnProperty(p)) A[A.length]= what[p];
}
return A;
}
var N=Array.from(document.getElementById("my_id").getElementsByTagName("*"))
while(N.length){
tem=N.shift();
}