我应该如何以索引顺序迭代稀疏数组?

时间:2014-12-22 07:29:56

标签: javascript arrays sparse-array

我有一个稀疏数组,其内容不能保证以索引顺序插入,但需要按索引顺序迭代。要遍历稀疏数组,我了解您需要使用for..in语句。

然而,根据this article

  

无法保证for ... in将以任何特定顺序返回索引

但是stackoverflow questions like this表明虽然不保证对象属性订单,但是数组顺序是:

  

在JavaScript中不保证对象中的属性顺序,您需要使用数组。

我在最新版本的Chrome,Firefox和IE中tested this

<ol id="items"></ol>
var list = [];

function addItem(index) {
    list[index] = { idx : index };
}

var insertOrder = [ 8, 1, 9, 2, 10, 3, 11, 4, 12, 5, 13, 6, 14, 7, 15 ];

for ( var i = 0; i < 15; i++ ) {
    addItem(insertOrder[i]);
}

for(var item in list) {
    $("#items").append("<li>" + list[item].idx + "</li>");
}

所有人似乎都尊重索引顺序,所以我是否可以相信这一点?否则,我如何以索引顺序最好地获取它们?

2 个答案:

答案 0 :(得分:12)

MDN可以回答您原来的问题:

  

注意:for..in不应该用于迭代索引顺序很重要的数组。

     

数组索引只是具有整数名称的可枚举属性,并且与一般对象属性相同。无法保证for ... in将以任何特定顺序返回索引,并且它将返回所有可枚举属性,包括具有非整数名称和继承的属性。

您不必使用for..in来遍历稀疏数组,如果可以的话,您应该definitely avoid doing so

您可以使用.forEach

list.forEach(function (el) {  // add a second parameter if you need the indices
    $("#items").append($("<li>").text(el.idx));
});

forEach is defined按索引顺序迭代,只包含数组中的元素:

  

forEach按升序为数组中的每个元素执行一次提供的回调。对于已删除或省略的索引,不会调用它。但是,它对存在的元素执行并且值未定义。


如果您要定位不支持forEach的环境,则可以使用以下内容或该MDN页面上提供的填充程序:

for (var i = 0; i < list.length; i += 1) {
    if (i in list) {
        $("#items").append($("<li>").text(list[i].idx));
    }
}

答案 1 :(得分:0)

ECMAScript 2015中for ...的for ...仅迭代数组数据(不是原型方法)并保证顺序。请参阅MDN https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Statements/fBlockquoteor...of和此答案:Does "for...of" loop iteration follow the array order in JavaScript?

请参阅Access to ES6 array element index inside for-of loop以获取索引。请注意,for..of迭代数组中未定义的空洞/空值,因此如果您不想要这些,则需要检查key in array

此处进一步讨论:https://groups.google.com/forum/#!topic/strengthen-js/jj7UX-fU-_A - 建议javascript缺少有序的地图数据结构。