Undercore:查找数组中出现频率最高的对象

Underscore: Find the most frequently occurring object in an array?

本文关键字:频率 对象 查找 数组 Undercore      更新时间:2023-09-26

这里有一个对象数组。

var list = [
    {"id": 439, "name": "John"},
    {"id": 439, "name": "John"},
    {"id": 100, "name": "Kevin"},
    {"id": 120, "name": "Max"},
    {"id": 439, "name": "John"}
];

我需要从这个数组中提取最频繁出现的对象,并按照最流行的名称构建一个新的数组。

到目前为止,我已经试着遵循这个主题中的方法:Underscore.js:在数组中找到最频繁出现的值?

// Build temp list
temp_list = _(
    _.chain(
        _(list).pluck('id')
    )
    .countBy()
    .pairs()
    .value()
)
.sortBy(1)
.reverse();
// Build final list with most frequently occurring first
_.map(temp_list, function(current) {
    return _.findWhere(list, {
        'id': parseInt(current[0])
    });
});

是否有一种方法可以通过直接排序初始列表来改进此代码,而无需创建临时列表?

您几乎已经做到了:您可以在reverse调用后立即调用map。我是这样做的:

var newlist = _.chain(list)
    .countBy(function (item) { return item.id; })
    .pairs()
    .sortBy(function (item) { return item[1]; })
    .reverse()
    .map(function (item) { return _.findWhere(list, { id: parseInt(item[0]) }); })
    .value();

细分:

chain:返回数组的包装版本,让您将下划线函数串起来。

countBy:返回一个对象,其中键是从回调返回的任何值,值是这些键出现的次数。

:将{ key: 'value' }转换为['key', 'value']

sortBy:返回一个按回调返回的值排序的数组

反转:反转阵列

map:返回一个新数组,其中每个项都基于该索引处原始数组中的项,以及在回调中对该值所做的任何操作。在这种情况下,我们使用iditem[0])从原始列表中获取对象。

:打开可链接对象并返回";生的";价值

_.chain(list)
    .countBy("id").pairs().sortBy()
    .reverse().map(function (element) {return _.findWhere(list, { id: parseInt(element[0]) }); }).value()

var list = [
    {"id": 439, "name": "John"},
    {"id": 439, "name": "John"},
    {"id": 100, "name": "Kevin"},
    {"id": 120, "name": "Max"},
    {"id": 439, "name": "John"}
];
var result = _.chain(list)
    .countBy("id").pairs().sortBy()
    .reverse().map(function (element) {return _.findWhere(list, { id: parseInt(element[0]) }); }).value();
console.log(result);
document.write(JSON.stringify(result));
<script src="https://cdnjs.cloudflare.com/ajax/libs/underscore.js/1.8.3/underscore-min.js"></script>

您可以使用reduce来获取项目计数,然后使用sortBy

像这样的

var list = [
    {"id": 439, "name": "John"},
    {"id": 439, "name": "John"},
    {"id": 100, "name": "Kevin"},
    {"id": 120, "name": "Max"},
    {"id": 439, "name": "John"}
];
var finalList = _.chain(list)
	.reduce(function(memo, item){
	var previous = _.findWhere(memo,{id:item.id});
  if(previous){
  	previous.count++;
  }else{
  	item.count=1;
  	memo.push(item);
  }
  return memo;
},[])
	.sortBy('count')
  .reverse()
  .value();
<script src="https://cdnjs.cloudflare.com/ajax/libs/underscore.js/1.8.3/underscore-min.js"></script>