【问题标题】:Iterate an object on a specific order按特定顺序迭代对象
【发布时间】:2018-03-20 04:07:51
【问题描述】:

我有一些这样的 JSON:

{ 
"a": { "text": "text", "index": 5 },
"b": { "text": "text", "index": 3 },
"c": { "text": "text", "index": 1 },
} 

现在我需要对这个对象进行交互,并在第一级的每个属性(a、b 和 c)上调用一个函数,但我必须使用“index”属性按顺序执行,比如首先使用“c”,然后是“b”,最后是“a”。

但是我读到我不应该使用 for in 循环:

for...in 循环以任意顺序迭代对象的属性(请参阅 delete 运算符以了解更多关于为什么不能依赖迭代的看似有序性,至少在跨浏览器设置中)。

那我该怎么做呢?

谢谢

【问题讨论】:

  • 你能复制一份,排序然后然后操作吗?或者您希望在没有副本的情况下执行此操作?我可以想象用while 循环来做这件事,但这似乎很繁重......
  • 是的,我认为复制是可以接受的
  • 复制会有点不雅和不必要 - 只需使用本机数组方法。

标签: javascript json javascript-objects


【解决方案1】:

你可以,

  1. 使用Object.keys()以数组形式获取对象的属性。
  2. 使用sort()对对象的属性进行排序。
  3. 使用forEach() 遍历已排序的项目(按数组的升序执行)。

var items = {
  "a": {
    "text": "text",
    "index": 5
  },
  "b": {
    "text": "text",
    "index": 3
  },
  "c": {
    "text": "text",
    "index": 1,
  }
};

Object.keys(items).sort(function(a, b) {
  return items[a].index - items[b].index;
}).forEach(doStuff);

function doStuff(key) {
  console.log(items[key]);
}

【讨论】:

    【解决方案2】:

    您可以使用getOwnPropertyNames

    let obj = { 
      "a": { "text": "text", "index": 5 },
      "b": { "text": "text", "index": 3 },
      "c": { "text": "text", "index": 1 }
    };
    
    function test(p) { 
        console.log(p);
    }
    
    Object.getOwnPropertyNames(obj)
          .reverse() 
          .forEach(function(p){
             test(obj[p]);
          });

    【讨论】:

    • 它确实从 a - b - c 迭代,但是如何反转或排序迭代?
    • @StefansArya getOwnPropertyNames 返回一个数组。只需调用 reverse() 即可。我已经更新了答案
    【解决方案3】:

    您可以尝试以下方法:

    1. 将对象转换为一个数组,其中元素按索引排序。
    2. 而不是简单地 forEach() 对已排序的属性。

    排序功能可以实现为:

    var obj = { 
    "a": { "text": "text", "index": 5 },
    "b": { "text": "text", "index": 3 },
    "c": { "text": "text", "index": 1},
    }
    
     function sortProperties(obj, sortedBy, isNumericSort, reverse) {
                sortedBy = sortedBy || 1; // by default first key
                isNumericSort = isNumericSort || false; // by default text sort
                reverse = reverse || false; // by default no reverse
    
                var reversed = (reverse) ? -1 : 1;
    
                var sortable = [];
                for (var key in obj) {
                    if (obj.hasOwnProperty(key)) {
                        sortable.push([key, obj[key]]);
                    }
                }
                if (isNumericSort)
                    sortable.sort(function (a, b) {
                        return reversed * (a[1][sortedBy] - b[1][sortedBy]);
                    });
                else
                    sortable.sort(function (a, b) {
                        var x = a[1][sortedBy].toLowerCase(),
                            y = b[1][sortedBy].toLowerCase();
                        return x < y ? reversed * -1 : x > y ? reversed : 0;
                    });
                return sortable; // array in format [ [ key1, val1 ], [ key2, val2 ], ... ]
            }
            
            sortProperties(obj, 'index', true, false);

    【讨论】:

      【解决方案4】:

      另一种解决方案是存储对象键并将其反转,然后使用对象键进行迭代。

      var obj = { 
      	"a": { "text": "text", "index": 5 },
      	"b": { "text": "text", "index": 3 },
      	"c": { "text": "text", "index": 1 }
      };
      var yourFunction = console.log;
      var keys = Object.keys(obj);
      keys.reverse();
      for (var i = 0; i < keys.length; i++) {
      	yourFunction(obj[keys[i]]);
      }

      【讨论】:

      • 您似乎没有对数据进行排序。把它倒过来。
      【解决方案5】:

      如果您想以相反的顺序访问 json 项,也可以使用 javascript 的 reverse() 方法。
      使用 Object.keys()
      获取 json 的所有键的数组 使用 reverse() 方法反转数组
      最后,您可以使用 javascript forEach() 方法来处理 json 的项目。示例代码如下所示

      let obj = {
      "a": { "text": "text", "index": 5 },
      "b": { "text": "text", "index": 3 },
      "c": { "text": "text", "index": 1 },
      }
      
      Object.keys(obj)
                  .reverse()
                  .forEach(ele => {
                    console.log(obj[ele]);
                  });
      

      访问This link了解更多reverse()方法

      【讨论】:

        【解决方案6】:

        您可能应该使用Object.keys 来获取所有属性的列表,对该列表进行排序,然后对其进行迭代。

        【讨论】:

        • @connexo 甚至可以说它是一个
        • @connexo 把它带到 Meta。我的回答不正确吗?我实际上确实希望该网站会说“将琐碎的答案转换为评论”。
        猜你喜欢
        • 2017-02-19
        • 2019-07-18
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        相关资源
        最近更新 更多