web-dev-qa-db-fra.com

Pourquoi "for (var item in list)" avec les tableaux considérés comme une mauvaise pratique en JavaScript?

Étant donné un tableau indexé numériquement basé sur zéro:

var list = ['Foo', 'Bar', 'Baz'];

Plusieurs fois, j'ai remarqué que lorsque quelqu'un suggère de parcourir en boucle des variables dans un tableau comme celui-ci:

for(var item in list) { ... }

... il y a presque certainement quelqu'un qui suggère que c'est une mauvaise pratique et suggère une approche alternative:

var count = list.length;

for(var i = 0; i < count; i++) {
    var item = list[i];
    ...
}

Quel est le raisonnement pour ne pas utiliser la version simplifiée ci-dessus et pour utiliser le deuxième exemple à la place?

67
Tatu Ulmanen

Tout d'abord, l'ordre de la boucle n'est pas défini pour une boucle for...in; il n'y a donc aucune garantie que les propriétés seront itérées dans l'ordre souhaité.

Deuxièmement, for...in parcourt toutes les propriétés énumérables d'un objet, y compris celles héritées de son prototype. Dans le cas des tableaux, cela pourrait vous affecter si votre code ou l'une des bibliothèques incluses dans votre page a augmenté le prototype de Array, ce qui peut être une chose réellement utile:

Array.prototype.remove = function(val) {
    // Irrelevant implementation details
};

var a = ["a", "b", "c"];

for (var i in a) {
    console.log(i);
}

// Logs 0, 1, 2, "remove" (though not necessarily in that order)
82
Tim Down

La vitesse? 

La boucle for(..;..;..) s’est révélée être 36 fois plus rapide que for .. inlorsque je l’ai testée ici.

Lien courtoisie cette SO réponse

16
Amarghosh

Si vous utilisez for/in comme cela, item énumère les valeurs de chaîne "0", "1", ..., donc pas les objets réels de la liste. Ainsi, l'élément dans le premier extrait ressemble davantage à i dans le deuxième extrait et non à item. De plus, les valeurs de chaîne sont énumérées là où vous vous attendez à des chiffres. Et vous avez des problèmes lorsque vous ouvrez des propriétés dans la liste, telles que array.ID = "a123", car elles seront également énumérées. 

Mais avec ces inconvénients, je pense toujours que la syntaxe est très utile si votre équipe est au courant de ce qu’elle fait. 

1
user180326

Ajoutez list.foo = bar; et essayez d’utiliser la variable for..__ simple. Si vous n’utilisez pas certaines bibliothèques (comme prototypeJs) et n’ajoutez aucune nouvelle propriété à l’objet tableau - vous pouvez utiliser une instruction for simple.

0
Adelf