面试官:JavaScript对象属性是有序的吗?
source link: https://www.fly63.com/article/detial/11897
Go to the source link to view the article. You can view the picture content, updated content and better typesetting reading experience. If the link is broken, please click the button below to view the snapshot at that time.
扫一扫分享
最近有人问我,JavaScript对象属性是否一定是无序的、不可预测的?
早期接触过JavaScript的开发者可能会回答, Object.keys() 或 for...in 会返回一个不可预知的对象属性顺序。
但现在的情况仍然是这样吗?
不是了,有些情况下是有序的。
从ECMAScript 2020开始, Object.key 、 for...in 、 Object.getOwnPropertyNames 和 Reflect.ownKeys 都遵循同一个规范顺序。它们是:
1. 自己的属性是数组的索引,按数字索引升序排列
const obj = {
100: 100,
'2': 2,
12: 12,
'0': 0
}
// 下面打印的结果顺序都是 ['0', '2', '12', '100']
console.log(Object.keys(obj))
console.log(Object.getOwnPropertyNames(obj))
console.log(Reflect.ownKeys(obj))
for (const key in obj) {
console.log('key', key)
}
const obj = {
a: 'a',
};
obj.b = 'b';
setTimeout(() => {
obj.c = 'c';
});
obj.d = 'd';
// 下面打印的结果顺序都是 `[ 'a', 'b', 'd' ]`
console.log(Object.keys(obj));
console.log(Object.getOwnPropertyNames(obj));
console.log(Reflect.ownKeys(obj));
for (const key in obj) {
console.log('key: ', key);
}
上面的代码添加了事件循环的知识点。因为 setTimeout 是一个异步的宏任务,当 console.log 输出时, c 属性还没有被添加到 obj 中。
2. 自身的 Symbol 属性,按创建时间顺序递增
const obj = {
[Symbol('a')]: 'a',
[Symbol.for('b')]: 'b',
};
obj[Symbol('c')] = 'c';
console.log(Object.keys(obj)); // []
console.log(Object.getOwnPropertyNames(obj)); // []
console.log(Reflect.ownKeys(obj)); // [ Symbol(a), Symbol(b), Symbol(c) ]
for (const key in obj) {
console.log('key: ', key); // 没有输出
}
console.log(Object.getOwnPropertySymbols(obj)); // [ Symbol(a), Symbol(b), Symbol(c) ]
Symbol 属性和 String 属性一样,是按照属性创建的时间顺序升序排列的。但是 Object.key , for...in , Object.getOwnPropertyNames 方法不能获得对象的 Symbol 属性, Reflect.ownKeys 和 Object.getOwnPropertySymbols 可以。
当一个对象的属性键是上述类型的组合时,该对象的非负整数键(可枚举和不可枚举)首先按升序添加到数组中,然后按插入顺序添加字符串键。最后,Symbol 键按插入顺序加入。
const obj = {
100: 100,
0: 0,
a: 'a',
[Symbol('a')]: 'a',
};
obj[Symbol.for('b')] = 'b';
obj.b = 'b';
console.log(Object.keys(obj)); // [ '0', '100', 'a', 'b' ]
console.log(Object.getOwnPropertyNames(obj)); // [ '0', '100', 'a', 'b' ]
console.log(Reflect.ownKeys(obj)); // [ '0', '100', 'a', 'b', Symbol(a), Symbol(b) ]
for (const key in obj) {
console.log('key: ', key); // '0' '100' 'a' 'b'
}
console.log(Object.getOwnPropertySymbols(obj)); // [ Symbol(a), Symbol(b) ]
但是,如果你强烈依赖插入顺序,那么Map可以保证这一点。
作者:islizeqiang,译者:小智
原文:https://medium.com/@islizeqiang/are-javascript-object-properties-ordered-c30597754e5c
Recommend
-
10
问题重现 需求是要获取一个车型列表,并且输出到页面上按年份排序,故而接口提供的对象简化如下 let obj = { '2018': { modelCode: "204313", modelName: "2018款 Vanquish 6.0L S Coupe"...
-
25
本文介绍下Java对象属性复制组件(MapStruct),以及项目中引入遇到的坑。 1. 问题背景 日常编程中,经常会碰到对象属性复制的场景,就比如下面这样一个常见的三层MVC架构。
-
10
细说JavaScript中对象的属性和方法 原创 ...
-
1
1、writable:可写 writable表示是否可以设置属性的值 let obj = {age:10} obj.age = 1 // 给...
-
5
面试官:Redis中基本的数据类型有哪些? 我:Redis的基本数据类型有:字符串(string)、哈希(hash)、列表(list)、集合(set)、有序集合(zset)。 面试官:有序集合的内部实现方式是什么?
-
9
#yyds干货盘点# 面试必刷TOP101:删除有序链表中重复的元素-II 原创 97的风
-
1
...
-
6
...
-
4
JavaScript 对象自身属性 在本教程中,您将了解 JavaScript 对象的自身属性 Own Properties
-
4
五种在 JavaScript 中访问对象属性的方法 作者:佚名 2023-06-02 15:42:51 在 JavaScript 中,对象是语言的基本组成部分,广泛用于表示数据结构。对象由保存值的属性组成。为了访问这些属性,JavaScript 提供了多...
About Joyk
Aggregate valuable and interesting links.
Joyk means Joy of geeK