Explain the order of JS object traversal in detail

  • 2021-11-13 00:43:13
  • OfStack

Some students may have heard this 1 saying that the order of traversing objects in JavaScript is not fixed. In fact, this statement is not particularly accurate.

Objects have their own set of rules for traversal order. Under this rule, the traversal order of objects will be affected by the order of inserting elements, but not completely affected by the order of inserting elements. If you have a scenario where you have to traverse in the order in which you insert elements, consider using Map.
There are many ways to traverse objects. We often use for... in. In addition, there are:

Object.keys Object.entries Obejct.getOwnerProPertyNames Reflect.ownKeys ......

The methods listed above all traverse objects according to the same rules. The actual traversal rules will vary according to the key value type.
In 1 object, if our key value is a positive integer string like '1', '200'. The order of traversal is arranged according to the size of key value.
For example, let's look at such an example:


const obj = {}

obj['10'] = 'a';
obj['9'] = 'b';
obj[8] = 'c';
obj[7] = 'd';

console.log(Object.keys(obj)) //  ["7", "8", "9", "10"]

Our final traversal order completely ignores the insertion order, and it is worth noting that in objects, even if the index value when we add attributes is of type Number, the final result will be implicitly converted to a string.

Array, as a kind of object, also conforms to the above rules, or perhaps, the above performance is because it is compatible with arrays. In addition, from the above rules, we can infer that the traversal of class arrays (key values are positive integers and have length attributes) is also in indexed order.
In addition, if our key value is a string that cannot be converted to a positive integer, this includes strings that can be converted to negative numbers (such as'-1 '), strings in decimal format (such as' 1.0 ') and other strings. Their traversal order will be more intuitive, that is, the order in which objects are inserted:


const obj2 = {}

obj2['1.1'] = 'a';
obj2['1.0'] = 'b';
obj2['-1'] = 'c';
obj2['jack'] = 'd'

console.log(Object.keys(obj2)); //  ["1.1", "1.0", "-1", "jack"]

In fact, the index value of an object can be not only a string, but also an Symbol type. For the Symbol type, the traversal order is simply in the order in which the objects are inserted.

If our object combines all the above, that is, the index value of 1 object appears all types (various forms of strings, Symbol type), it will:

First, traverse the positive integer part according to the rules we mentioned above about positive integers Traverse the remaining strings in the order in which they will be inserted next Finally, the Symbol type is traversed in the insertion order

I believe that by this point, everyone has fully understood the traversal order of objects. Finally, there is one point worthy of attention, which is the traversal order of for... in.

At the beginning, there was no standard for the traversal order of for... in, and browser manufacturers would set the traversal order of for... in according to their preferences. If you have a requirement for traversal order and want to be compatible with an older browser version, it is not recommended to use it. Later, a proposal of ES 2019 regulated this phenomenon, and now the order of for... in also follows the above rules.

Although the rules above are followed, for... in also traverses the properties of the prototype. Therefore, the rule of for... in variable element is to go to the variable object itself according to the object traversal rule mentioned above, then traverse the prototype of the object according to this rule, and so on, until traversing to the top.

Except for the last one for... in, there is nothing else. In fact, there is less content.


Related articles: