在 javascript 中对嵌套对象的对象进行排序(可能使用 lodash?)

Sorting an object of nested objects in javascript (maybe using lodash?)

我有一个嵌套对象的对象,想按嵌套值之一排序(例如 "month_sales" 降序)。这是数据的样子:

{ 
"Bob": { sales: 13, revenue: 33, month_sales: 149 },
"Bill": { today_sales: 20, week_sales: 38, month_sales: 186 },
"Jane": { today_sales: 17, week_sales: 38, month_sales: 164 }
}

这就是我想要的样子(按 month_sales 降序排序):

{ 
"Bill": { today_sales: 20, week_sales: 38, month_sales: 186 },
"Jane": { today_sales: 17, week_sales: 38, month_sales: 164 }
"Bob": { sales: 13, revenue: 33, month_sales: 149 },
}

我遍历了 Google 和 Whosebug,只找到了几个处理对象排序而不是数组排序的答案,并且在每种情况下答案都是 "write a function to convert the object to an array, sort that, and then turn it back into an object."

作为最后的手段,我愿意这样做,但似乎我应该能够做到这一点,而无需解构整个对象并将其重新组合在一起。也许有一种优雅的方法可以在 lodash 或其他东西中做到这一点?

这是不可能的,因为对象的属性在 javascript 中没有保证的顺序。您可能必须首先将其转换为数组:

[ 
  { name: "Bob", sales: 13, revenue: 33, month_sales: 149 },
  { name: "Bill", today_sales: 20, week_sales: 38, month_sales: 186 },
  { name: "Jane", today_sales: 17, week_sales: 38, month_sales: 164 }
]

然后,当您将其作为数组进行排序时,它将保持该顺序。

如果将对象转换为数组,则可以像这样按类别对它们进行排序

var arr = [ 
  { name: "Bob", sales: 13, revenue: 33, month_sales: 149 },
  { name: "Bill", today_sales: 20, week_sales: 38, month_sales: 186 },
  { name: "Jane", today_sales: 17, week_sales: 38, month_sales: 164 }
]

arr.sort(function(x, y){
    var category = "month_sales"
    if (x[category] < y[category]) {
        return -1;
    }
    if (x[category] > y[category]) {
        return 1;
    }
    return 0;
});

虽然您无法对对象进行排序,但您可以创建一个索引,根据您想要的 属性 进行排序,例如获取按 month_sales 从高到低排序的姓名列表:

var obj = { 
"Bob": { sales: 13, revenue: 33, month_sales: 149 },
"Bill": { today_sales: 20, week_sales: 38, month_sales: 186 },
"Jane": { today_sales: 17, week_sales: 38, month_sales: 164 }
}

var index = Object.keys(obj).sort(function(a,b) {
              return obj[b].month_sales - obj[a].month_sales;
            });

然后取最高值的:

console.log(index[0] + ':' + obj[index[0]].month_sales); // Bill:186

只能排序数组,不能排序对象。为此,您首先需要将您的对象 map 到一个数组。以下是使用 lodash map() and sortBy():

的方法
_(data)
    .map(function(value, key) {
        return _.defaults({ name: key }, value);
    })
    .sortBy('name')
    .value();
// →
// [
//   { name: "Bill", today_sales: 20, week_sales: 38, month_sales: 186 },
//   { name: "Bob", sales: 13, revenue: 33, month_sales: 149 },
//   { name: "Jane", today_sales: 17, week_sales: 38, month_sales: 164 }
// ]

映射使用defaults()函数给每个数组项一个新的name属性,用来对数组进行排序