Google Chrome: Assoziative JavaScript-Arrays, die außerhalb der Reihenfolge ausgewertet werden

7

Ok, auf einer Webseite habe ich ein JavaScript-Objekt, das ich als assoziatives Array benutze. Dies geschieht statisch in einem Skriptblock, wenn die Seite geladen wird:

%Vor%

Die Reihenfolge der Schlüssel / Wert-Paare ist beabsichtigt, da ich das Objekt in ein HTML-Auswahlfeld wie dieses verwandle:

%Vor%

... mit Code, der so aussieht (von einer Funktion abgeschnitten):

%Vor%

Das alles funktioniert in IE, FireFox und Opera.

In Chrome erscheint die Reihenfolge jedoch seltsam:

%Vor%

HINWEIS: Diese Reihenfolge, obwohl seltsam, ändert sich nicht bei nachfolgenden Aktualisierungen. Es ist immer in dieser Reihenfolge.

Was macht Chrome? Einige Optimierung in wie es die Schleife verarbeitet?

An der ersten Stelle bin ich falsch, auf die Reihenfolge zu vertrauen, dass die Schlüssel / Wert-Paare in irgendeinem assoziativen Array erklärt werden?

Ich habe es nie zuvor in Frage gestellt, ich habe einfach angenommen, dass die Reihenfolge eingehalten werden würde, weil diese Technik in den anderen Browsern immer für mich funktioniert hat. Aber ich nehme an, dass ich nirgends gesagt habe, dass die Bestellung garantiert ist. Vielleicht ist es nicht?

Jede Einsicht wäre großartig. Danke.

    
Jerry 12.03.2009, 22:28
quelle

7 Antworten

10

Stellen Sie sich ein assoziatives Array als einen Papiersack vor, in den alle Schlüssel / Wert-Paare platziert werden. Wenn du deine Hand in den Sack greifst, um die Paare zu betrachten (zum Beispiel mit der for ... in-Schleife), ist die Reihenfolge, in der du ihnen begegnest, praktisch zufällig.

Wenn Sie sie in einer bestimmten Reihenfolge sehen möchten, müssen Sie die Schlüssel in ein Array extrahieren und sortieren. Gehen Sie dann über das Array und verwenden Sie die Tasten, die Sie zum Indexieren in das assoziative Array finden.

    
Barry Brown 12.03.2009, 22:42
quelle
8

Die Reihenfolge, in der Elemente in einem assoziativen Array gespeichert werden, ist nicht garantiert. Sie müssen Ihre Ausgabe explizit sortieren.

    
moonshadow 12.03.2009 22:33
quelle
2

Wie die anderen Antworten sagen, ist die Reihenfolge, in der die Eigenschaften eines Objekts iteriert werden, nicht in der Spezifikation definiert, obwohl die Hauptbrowser sie alle in der definierten Reihenfolge durchlaufen.

Chrome zählt sie auch in der Reihenfolge auf, wenn alle Eigenschaften des Objekts primitive Werte enthalten. John Resig gibt hier mehr Details zum Chrome-Verhalten (unter "for loop order"): Ссылка

    
Gabe Moothart 12.03.2009 23:10
quelle
2

Wie bereits erwähnt, ist das Verhalten von Chrome absolut korrekt.

Dies ist ein guter Fall, in dem ein OO-Denken helfen kann. Möchten Sie wirklich ein assoziatives Array oder nur eine Liste von Objekten?

%Vor%

würde Ihnen besser dienen, denke ich (denen, die irgendeine Form der Sortierung befürworteten, ist die Reihenfolge bereits definiert - warum möchten Sie zusätzliche Arbeit leisten?)

    
CurtainDog 24.05.2010 22:20
quelle
2

@curtainDog: NEIN! NEIN! Die Verwendung von "for .. in" mit Array-Objekten in JavaScript ist schlecht - der Hauptpunkt der meisten Antworten hier ist, dass "for .. in" keine Reihenfolge garantiert. Darüber hinaus wird "for .. in" Eigenschaften aus dem Prototyp eines Objektkonstruktors abrufen und nicht über nicht vorhandene Schlüssel iterieren.

@Samnan: Die Spezifikation sagt einfach, dass die Iterationsreihenfolge nicht garantiert ist; Dies bedeutet, dass Browser frei sind, in sortierter Reihenfolge, in der Reihenfolge der Einfügung, in zufälliger Reihenfolge oder wie auch immer sie können, zu iterieren. Es ist wie ein Hashtable - man kann es als zufällig betrachten, auch wenn es zufällig erscheint.

Ich bin mir ziemlich sicher, dass die meisten Browser mit Array-Objekten nach "for..in" suchen und in numerischer Reihenfolge durchlaufen, damit die Dinge nicht kaputt gehen; es tut jedoch nicht wirklich, was die meisten Leute, die es benutzen, auf diese Weise denken, und es sollte vermieden werden, es sei denn, Sie benötigen speziell eine Objekt -Iteration.

    
Nomad128 23.01.2011 22:00
quelle
2

Es ist keine wirklich gute Übung, aber ...

Wenn Sie dem Wert ein Leerzeichen hinzufügen, berücksichtigt chrome den Wert nicht und sortiert sie nicht nach Wert.

Beispiel:

%Vor%

Die gute Seite ist, dass Sie keine alphabetischen Zeichen aus der ID hinzufügen und entfernen müssen, wie jemand vorgeschlagen hat (erinnern Sie sich nicht, ob in diesem oder einem anderen Beitrag mit ähnlicher Frage), Sie könnten es aber meistens schneiden Leerzeichen werden einfach ignoriert, und wenn Sie diese in eine andere Datei schreiben oder abrufen, sehen sie einfach den Integer-Wert und nicht das Leerzeichen.

    
Mauro 05.07.2012 22:08
quelle
-3

Im Gegensatz zu allen anderen Antworten ist es sicher ein Fehler in Chrom

Der Grund:

Wenn die Datenstruktur ein Papiersack ist, wie Barry sagte, dann:

Die Werte sollten immer randomisiert sein. Dies ist bei Chrom nicht der Fall.

Wenn die Datenstruktur sequentiell ist, dann:

Die Werte sollten in der Reihenfolge sein, in der sie der Struktur hinzugefügt wurden

Während andere Browser dem zweiten Ansatz folgen, folgt chrome weder und es gibt noch keine Erklärung dafür, was die Sortierreihenfolge ist, die chrome für die Datenstruktur ausfüllt, während auf sie zugegriffen wird.

    
Samnan 29.09.2010 13:44
quelle