var o={ '1': 1, “a”:2, “b”:3 } Object.keys(o);// [“1”、“a”、“b”]-此订单是否由ES6保证? for(让k输入o){ 控制台.log(k); }//1 2 3-此订单是否由ES6保证?
-
6 esdiscuss.org/topic/nailing-object-property-order – 戴夫·牛顿 评论 2015年5月6日12:07 -
三 Btw,用于 对象.获取自己的属性名称 , 对象.获取自己的属性符号 和 Reflect.own键 订单 是 定义。 – 贝吉 评论 2015年12月9日1:45 -
10 事实上-答案再次出现-不再是最新的:)ES2016为 对象.键 和 用于。。 在里面 循环和规范:19.1.2.16(Object.keys)调用7.3.21(EnumerateOwnProperties),这反过来保证:“对属性的元素进行排序,使它们的相对顺序与使用O调用Enumerate ObjectProperties内部方法时返回的Iterator生成的相对顺序相同。” -EnumerateOwnProperties反过来保证 [[自己的属性键]] (9.1.11)执行9.1.11.1(顺序所有属性键),以保证顺序。 – 本杰明·格伦鲍姆 评论 2017年7月17日14:43 -
三 这些数字来自ES2017规范(8),可在此处免费找到: ecma国际.org/ecma-262/8.0 – 本杰明·格伦鲍姆 评论 2017年7月17日14:43 -
6 @本杰明·格伦鲍姆我不知道在哪里 13.7.5.15 枚举对象属性 保证订单与 [[自己的属性键]] 它只说“ …必须通过调用[the]内部方法获得自己的属性键[…] “。获取后如何处理它们,或者如何将它们与继承的属性合并,都留给实现。 – 贝吉 评论 2017年8月22日22:49
3个答案
当的[[Enumerate]]内部方法 O(运行) 称为以下 采取以下步骤:
返回Iterator对象( 25.1.1.2 )其下一个方法迭代 的可枚举属性的所有字符串值键 O(运行) . The迭代器对象必须继承自%IteratorPrototype%( 25.1.2 ). 力学和 秩序 枚举属性的 不是 明确规定 但必须符合以下规定的规则 [1] .
如果实现为 for-in语句,[…]
整数索引(如果适用),按升序排列。 其他字符串键(如果适用),按属性创建顺序。 符号键(如果适用),按特性创建顺序。
log(Reflect.ownKeys(新代理({}{ own键:()=>['3','1','2'] }))); // ['3','1','2'],整数索引未排序!
[[Enumerate]]必须获取目标对象自己的属性键 犹如 通过调用其[[OwnPropertyKeys]]内部方法。
与迭代程序产生的相对顺序相同 如果调用了[[Enumerate]]内部方法,将返回
-
2 我实际上找不到getOwnPropertyNames如何保证订单的信息? 事实上,Firefox和Chrome的回归就是这样的 Object.getOwnPropertyNames({20:'a',10:'b'}) 这个 [ "10", "20" ] 数字排序而不是书面排序。 评论 2016年4月3日21:36 -
4 -
9 值得注意的是,虽然规范不需要 放弃 或 对象.键 按照顺序,当前版本的Firefox、Chrome和Edge都需要: jsfiddle.net/arhbn3k2/1 这很有道理,如果有多个枚举实现,那就很奇怪了。 规范没有要求它,因为不同的引擎已经有了不同于新定义顺序的行为,委员会不想要求实现可能破坏现有代码。 不过,这些实现似乎已经决定; Firefox的订单过去肯定有所不同。 – T.J.克劳德 评论 2017年11月3日8:40 -
三 @user10089632哈哈! 好问题。。。 答案 可以 就是那个旧代码 应该 被打破也行……至少在这方面! 我认为,这可能导致异常在应该抛出的时候没有抛出,并完全改变行为。 然而,我怀疑更新后的规格是否在所有情况下都像那样严格。 – 麦克啮齿动物 评论 2017年11月16日10:30 -
三 @52d6c6af-这是正确的 2015年欧洲标准 具体来说,不需要 对象.键 这样才能遵循新的秩序。 这在ES2020中是不正确的 做 现在需要它,尤其是因为引擎已经更新了(请参阅我2017年的评论)。由于Oriol不再为so提供帮助,我在答案的顶部添加了一个注释。 – T.J.克劳德 评论 2020年3月24日15:23
如果实现为for-in语句定义了特定的枚举顺序,那么必须对步骤3中返回的数组元素使用相同的顺序。
对的元素排序 属性 因此,它们的相对顺序与使用调用EnumerateObjectProperties内部方法时返回的Iterator生成的相对顺序相同 O(运行) .
拥有的属性 数组索引 , 1 以升序数字索引顺序 其他自己的String属性,按属性创建的时间升序排列 自己的符号属性,按属性创建的时间升序排列
-
提出了一个问题,即当使用相同的操作插入属性时,它们会得到什么顺序。 例如,对象文字或 Object.assign() 在后一种情况下,它可能是词汇的,也可能来自输入对象,但它必须这样吗? – 罗伯特·西默 评论 2020年3月17日17:33 -
1 @RobertSiemer——这在规范中得到了很好的定义:对象文本中的属性是按源代码顺序添加的(这永远是正确的) 对象分配 (和属性排列)遵循源对象的属性顺序。 所以 对象.键({a:1,b:2}) (现在)是可靠的 [“a”、“b”] 和 对象.键({b:2,a:1}) (现在)是可靠的 [“b”、“a”] 。但一般来说,最好不要依赖于对象属性的迭代顺序。 依赖创建/分配的顺序很好(并且常见: const-copy={…original,x:true}; 可靠地创造结果 副本。 x个 存在 真的 ). :-) – T.J.克劳德 评论 2020年3月24日15:28