Closed Bug 865760 Opened 11 years ago Closed 11 years ago

Javascript object keys are now sorted

Categories

(Core :: JavaScript Engine, defect)

21 Branch
x86_64
Windows 7
defect
Not set
normal

Tracking

()

RESOLVED INVALID

People

(Reporter: jwalton, Unassigned)

References

Details

Attachments

(1 file)

Attached file test.html
User Agent: Mozilla/5.0 (Windows NT 6.1; WOW64; rv:20.0) Gecko/20100101 Firefox/20.0
Build ID: 20130409194949

Steps to reproduce:

<html>
<body>
<script>
var obj = { "10": "Harry", "a": "x", "123": "Bob", "1": "Larry", "2": "Joe" };
for( x in obj ) {
  console.log(x);
}
</script>
</body>
</html>



Actual results:

Version 21:

1
2
10
123
a



Expected results:

Version 20 and before:
10
a
123
1
2
Assignee: nobody → general
Component: Untriaged → JavaScript Engine
Product: Firefox → Core
I've found out, that if i put in a key that is >999 then it sorts correct.  Seems like there is some code, that takes all numeric keys, if they are under 1000, and puts them at the beginning and then sorts them numerically, all other alpha keys are sorted as they are entered.

So { "100":"", "aaaaa": "", "b": "", "10": "", "a": "", "123": "", "1": "", "2": "" }

shows

1
2
10
100
123
aaaaa
b
a

where as

{ "1000":"", "aaaaa": "", "b": "", "10": "", "a": "", "123": "", "1": "", "2": "" }

displays

1000
aaaaa
b
10
a
123
1
2

Which is correct
Behavior here changed as a result of bug 827490 --- plain objects now use a more efficient representation for indexed properties.  All the object's keys won't be sorted; indexed properties will usually appear first in sorted order, followed by non-indexed properties in the order they were added.  When the 1000 appears first it is because we fell back to another representation that is used when the object's indexes are very sparse.

There is no "correct" or "incorrect" here, as enumeration order is not part of the JavaScript spec.  The new behavior is closer to what Chrome has been doing for years.
Yeah, enumeration ordering is unspecified.  Don't rely on it!
Status: UNCONFIRMED → RESOLVED
Closed: 11 years ago
Resolution: --- → INVALID
(In reply to Brian Hackett (:bhackett) from comment #2)
> There is no "correct" or "incorrect" here, as enumeration order is not part
> of the JavaScript spec.  The new behavior is closer to what Chrome has been
> doing for years.

(In reply to Jeff Walden [:Waldo] (remove +bmo to email) from comment #3)
> Yeah, enumeration ordering is unspecified.  Don't rely on it!

There was maybe plan to make the enumeration deterministic [1] for ES6. Asking to es-discuss where this is at.

[1] http://wiki.ecmascript.org/doku.php?id=strawman:enumeration
The fallback at 1000 makes an interop hazard vs. V8 at least, probably JSC too. It's also a pain even ignoring interop, an inconsistency that will bite some code that inadvertently depends on no such threshold (just when running on a single implementation). It smells bad too :-P.

V8 seems to avoid such fallback. Why can't we?

ES7 will almost certainly standardize enumeration order. It may be close to what V8 does. We should try to converge now, not later -- that just makes a mess for developers, and for us marking their bugs INVALID, which bug-marking just annoys everyone.

/be
V8 separates storage for indexed vs. named properties, while we don't.  Getting a consistent enumeration order should fall out as a result of bug 586842, but with no eta there it would still be fairly straightforward to match that behavior right now.  Agreed the current behavior smells bad, but this interop hazard is not a new problem --- this bug was filed about the change in behavior from something nothing like the proposed spec/v8 behavior, to something fairly close to it.
You need to log in before you can comment on or make changes to this bug.

Attachment

General

Creator:
Created:
Updated:
Size: