Für mein aktuelles Projekt ist die IE8-Kompatibilität wichtig, und ich erwäge die Verwendung Polyfill von Mozillaaber ich bin mir nicht 100% sicher, wie das funktionieren wird.
Gibt es Unterschiede zwischen der standardmäßigen for-Schleife (das erste Beispiel oben) und der Array.prototype.forEach-Implementierung durch moderne Browser?
Gibt es einen Unterschied zwischen modernen Browserimplementierungen und der oben verlinkten Mozilla-Implementierung (insbesondere im Hinblick auf IE8)?
Die Leistung ist nicht so sehr ein Problem, sondern nur die Konsistenz, mit der Eigenschaften iteriert werden.
Es ist nicht möglich break aus forEach. Ein großer Vorteil ist jedoch, mit der Funktion einen neuen Geltungsbereich zu erstellen. Mit dem Polyfill solltest du keine Probleme haben (zumindest sind mir keine begegnet).
– hgoebl
12. Mai 2014 um 16:32 Uhr
Die Probleme, die Sie mit älteren IE haben können, ist nicht der Shim selbst, sondern der kaputte Array-Konstruktor/Literal wrt holes wo undefined sein sollte und andere kaputte Methoden, wie slice und hasOwnProperty wrt zu arrayartigen DOM-Objekten. Meine Prüfung u es5 shim haben gezeigt, dass solche Shim-Methoden mit der Spezifikation konform sind (MDN-Shim nicht getestet).
– Xotic750
12. Mai 2014 um 16:57 Uhr
Und bzgl. des Ausbruchs aus a for Schleife, das ist was some ist für.
– Xotic750
12. Mai 2014 um 16:59 Uhr
“Ich kann jedoch anscheinend nichts finden, was die objektorientierte Schleife zu bevorzugen scheint:” Ich würde es eher funktional als zwingend nennen.
– Memke
29. November 2016 um 10:16 Uhr
Sie können verwenden Array.find() aus der Schleife auszubrechen, nachdem Sie eine erste Übereinstimmung gefunden haben.
– Mottie
25. Dezember 2016 um 14:44 Uhr
Alexis König
Der wesentlichste Unterschied zw for Schleife und die forEach Methode ist, dass Sie mit ersterem können break aus der Schleife. Sie können simulieren continue durch einfaches Zurückkehren von der Funktion, an die übergeben wurde forEachaber es gibt keine Möglichkeit, die Schleife ganz zu stoppen.
Abgesehen davon erfüllen die beiden praktisch die gleiche Funktionalität. Ein weiterer kleiner Unterschied betrifft den Gültigkeitsbereich des Indexes (und aller darin enthaltenen Variablen) in der for-Schleife aufgrund des Hebens von Variablen.
// 'i' is scoped to the containing function
for (var i = 0; i < arr.length; i++) { ... }
// 'i' is scoped to the internal function
arr.forEach(function (el, i) { ... });
Allerdings finde ich das forEach ist viel aussagekräftiger – es stellt Ihre Absicht dar, jedes Element eines Arrays zu durchlaufen, und liefert Ihnen eine Referenz auf das Element, nicht nur auf den Index. Insgesamt kommt es hauptsächlich auf den persönlichen Geschmack an, aber wenn Sie es verwenden können forEachwürde ich empfehlen, es zu verwenden.
Es gibt einige weitere wesentliche Unterschiede zwischen den beiden Versionen, insbesondere in Bezug auf die Leistung. Tatsächlich schneidet die einfache for-Schleife erheblich besser ab als die forEach Methode, wie gezeigt durch dieser Jsperf-Test.
Ob eine solche Leistung für Sie notwendig ist oder nicht, müssen Sie selbst entscheiden, und in den meisten Fällen würde ich Ausdrucksstärke der Geschwindigkeit vorziehen. Dieser Geschwindigkeitsunterschied ist wahrscheinlich auf die geringfügigen semantischen Unterschiede zwischen der grundlegenden Schleife und der Methode zurückzuführen, wenn mit Arrays mit geringer Dichte gearbeitet wird, wie in dieser Antwort angegeben.
Wenn Sie das Verhalten von nicht benötigen forEach und/oder Sie früh aus der Schleife ausbrechen müssen, können Sie Lo-Dash’s verwenden _.each als Alternative, die auch browserübergreifend funktioniert. Wenn Sie jQuery verwenden, bietet es auch eine ähnliche $.eachbeachten Sie einfach die Unterschiede in den Argumenten, die in jeder Variante an die Callback-Funktion übergeben werden.
(Wie für die forEach polyfill, es sollte in älteren Browsern problemlos funktionieren, wenn Sie sich für diesen Weg entscheiden.)
Es ist erwähnenswert, dass die Bibliotheksversionen each verhalten sich nicht wie die ECMA5-Spezifikation von forEach, neigen sie dazu, alle Arrays als dicht zu behandeln (um IE-Bugs zu vermeiden, vorausgesetzt, Sie sind sich dessen bewusst). Kann sonst ein “Gotcha” sein. Als Referenz github.com/es-shims/es5-shim/issues/190
– Xotic750
12. Mai 2014 um 17:01 Uhr
Außerdem gibt es einige Prototypmethoden, mit denen Sie brechen können, z Array.prototype.some was eine Schleife durchläuft, bis Sie einen wahren Wert zurückgeben oder bis es das Array vollständig durchlaufen hat. Array.prototype.every ist ähnlich wie Array.prototype.some aber stoppt, wenn Sie einen falschen Wert zurückgeben.
– axelduch
12. Mai 2014 um 17:15 Uhr
Wenn Sie einige Testergebnisse auf verschiedenen Browsern und solchen Shims sehen möchten, können Sie hier einen Blick darauf werfen. ci.testling.com/Xotic750/util-x
– Xotic750
12. Mai 2014 um 17:16 Uhr
Außerdem würde die Verwendung von Array.prototype.forEach Ihren Code der Gnade der Erweiterung aussetzen. Wenn Sie beispielsweise einen Code schreiben, der in eine Seite eingebettet werden soll, besteht die Möglichkeit, dass Array.prototype.forEach mit etwas anderem überschrieben wird.
– Marmordämon
19. August 2016 um 4:32 Uhr
@MarbleDaemon Die Wahrscheinlichkeit dafür ist so gering, dass es praktisch unmöglich und daher vernachlässigbar ist. Überschreiben Array.prototype.forEach mit einer nicht kompatiblen Version hätte das Potenzial, so viele Bibliotheken zu beschädigen, dass es sowieso nicht helfen würde, sie aus diesem Grund zu vermeiden.
– Alexis König
19. August 2016 um 4:54 Uhr
Möwe
Sie können Ihre benutzerdefinierte foreach-Funktion verwenden, die viel besser funktioniert als Array.forEach
Sie sollten dies einmal zu Ihrem Code hinzufügen. Dadurch wird dem Array eine neue Funktion hinzugefügt.
function foreach(fn) {
var arr = this;
var len = arr.length;
for(var i=0; i<len; ++i) {
fn(arr[i], i);
}
}
Object.defineProperty(Array.prototype, 'customForEach', {
enumerable: false,
value: foreach
});
Dann können Sie es überall wie Array.forEach verwenden
UPDATE: In der neuen Chrome-Version wurde die Leistung von .forEach() verbessert. Die Lösung kann jedoch die zusätzliche Leistung in anderen Browsern bereitstellen.
steviesch
Es wird von vielen Entwicklern (z. B. Kyle Simpson) zur Verwendung vorgeschlagen .forEach um anzuzeigen, dass das Array eine Nebenwirkung haben wird und .map für reine Funktionen. for Schleifen eignen sich gut als Allzwecklösung für eine bekannte Anzahl von Schleifen oder jeden anderen Fall, der nicht passt, da es aufgrund seiner breiten Unterstützung in den meisten Programmiersprachen einfacher zu kommunizieren ist.
z.B
/* For Loop known number of iterations */
const numberOfSeasons = 4;
for (let i = 0; i < numberOfSeasons; i++) {
//Do Something
}
/* Pure transformation */
const arrayToBeUppercased = ['www', 'html', 'js', 'us'];
const acronyms = arrayToBeUppercased.map((el) => el.toUpperCase));
/* Impure, side-effects with .forEach */
const acronymsHolder = [];
['www', 'html', 'js', 'us'].forEach((el) => acronymsHolder.push(el.toUpperCase()));
Konventionell scheint dies am besten zu sein, aber die Community hat sich nicht wirklich auf eine Konvention für das neuere Iterationsprotokoll geeinigt for in Schleifen. Im Allgemeinen denke ich, dass es eine gute Idee ist, den FP-Konzepten zu folgen, für die die JS-Community offen zu sein scheint.
11687500cookie-checkJavaScript – Nuancen von myArray.forEach vs. for-Schleifeyes
Es ist nicht möglich
break
ausforEach
. Ein großer Vorteil ist jedoch, mit der Funktion einen neuen Geltungsbereich zu erstellen. Mit dem Polyfill solltest du keine Probleme haben (zumindest sind mir keine begegnet).– hgoebl
12. Mai 2014 um 16:32 Uhr
Die Probleme, die Sie mit älteren IE haben können, ist nicht der Shim selbst, sondern der kaputte Array-Konstruktor/Literal wrt
holes
woundefined
sein sollte und andere kaputte Methoden, wieslice
undhasOwnProperty
wrt zu arrayartigen DOM-Objekten. Meine Prüfung ues5 shim
haben gezeigt, dass solche Shim-Methoden mit der Spezifikation konform sind (MDN-Shim nicht getestet).– Xotic750
12. Mai 2014 um 16:57 Uhr
Und bzgl. des Ausbruchs aus a
for
Schleife, das ist wassome
ist für.– Xotic750
12. Mai 2014 um 16:59 Uhr
“Ich kann jedoch anscheinend nichts finden, was die objektorientierte Schleife zu bevorzugen scheint:” Ich würde es eher funktional als zwingend nennen.
– Memke
29. November 2016 um 10:16 Uhr
Sie können verwenden
Array.find()
aus der Schleife auszubrechen, nachdem Sie eine erste Übereinstimmung gefunden haben.– Mottie
25. Dezember 2016 um 14:44 Uhr