如何按照编写的顺序迭代javascript对象属性

时间:2010-04-15 16:37:33

标签: javascript

我发现我的代码中存在一个错误,希望通过最少的重构努力来解决。 Chrome和Opera浏览器中会出现此错误。 问题:

var obj = {23:"AA",12:"BB"};
//iterating through obj's properties
for(i in obj)
  document.write("Key: "+i +" "+"Value: "+obj[i]);

FF,IE中的输出 关键:23价值:AA 关键:12价值:BB

Opera和Chrome中的输出(错误)
关键:12价值BB
关键:23价值AA

我试图制作一个像这样的逆序对象

var obj1={"AA":23,"BB":12};
for(i in obj1)
  document.write("Key: "+obj[i] +" "+"Value: "+i);

然而输出是相同的。有没有办法通过小的更改为所有浏览器提供相同的行为?

4 个答案:

答案 0 :(得分:20)

没有。 JavaScript对象属性没有固有的顺序。总算运气for...in循环的顺序是什么。

如果您想要订购,则必须使用数组:

var map= [[23, 'AA'], [12, 'BB']];
for (var i= 0; i<map.length; i++)
    document.write('Key '+map[i][0]+', value: '+map[i][1]);

答案 1 :(得分:2)

我认为你会发现唯一可行的方法是使用数组而不是关联数组,例如:

var arr = [{key:23,val:"AA"},{key:12,val:"BB"}];
for(var i=0; i<arr.length; i++)
  document.write("Key: "+arr[i].key +" "+"Value: "+arr[i].val);

答案 2 :(得分:0)

@bobince是正确的,对象不保持任何排序的元数据。

在我的情况下,它没有意义的重构为一个数组,所以我提出另一种解决方案:创建您的订购的数组,并用它来你的对象属性才能映射:

const obj = {
    'r': '#f00',
    'g': '#0f0',
    'b': '#00f',
};
const objMap = ['b','r','g'];

objMap.map((key, index) => {
    console.log(`array index: ${index}`);
    console.log(`object index: ${key}`);
    console.log(`object property: ${obj[key]}\n`);
});

输出:

array index: 0
object index: b
object property: #00f

array index: 1
object index: r
object property: #f00

array index: 2
object index: g
object property: #0f0

答案 3 :(得分:-2)

当对象属性标识符是字母字符串时,我没有得到你的结果。 IE8,FF5,Chrome 12和Opera 9.8都保留了创建顺序,即

键:AA值:23键:BB值:12

当标识符是结果与您匹配的数字时: -

IE8,FF5 - &gt;键:23值:AA键:12值:BB

Opera,Chrome - &gt;键:12值:BB键:23值:AA

Opera和Chrome以创建顺序的相反方式存储,因为12小于23,所以如果您使用,请说: -

var obj = {2:"AA",12:"BB"};

然后你得到所有4个浏览器的结果: -

键:2值:AA键:12值:BB

因此,使用数字作为标识符会导致差异。如果标识符是字母,则4个浏览器的创建和存储属性顺序都相同。尽管有ECMA规则,但存储的订单无需与创建订单相关。

如果字符串标识符是数字,例如'23'和'12',然后Opera和Chrome将它们视为数字并再次反转创建顺序,因此也不允许该类型。 “23a”类型可以和“a23”类型一样。

要回答您的问题,请使用非数字字符串标识符,并且4个浏览器(可能还有所有浏览器)的行为相同。