在Javascript中,我试图采取数字值的初始数组,并计算其中的元素。理想情况下,结果将是两个新数组,第一个数组指定每个唯一元素,第二个数组包含每个元素出现的次数。但是,我愿意听取关于输出格式的建议。

例如,如果初始数组是:

5, 5, 5, 2, 2, 2, 2, 2, 9, 4

然后将创建两个新数组。第一个将包含每个唯一元素的名称:

5, 2, 9, 4

第二个将包含该元素在初始数组中出现的次数:

3, 5, 1, 1

因为数字5在初始数组中出现了三次,数字2出现了五次,9和4都出现了一次。

我一直在寻找解决方案,但似乎没有一个可行,而且我自己尝试过的每件事最后都出奇地复杂。任何帮助都将不胜感激!

谢谢:)


当前回答

使用Lodash

Const值= [5,5,5,2,2,2,2,2,2,2,2,2,9,4]; const frequency = _.map(_.groupBy(values), val =>({值:val[0],频率:val.length})); console.log(频率); < script src = " https://cdnjs.cloudflare.com/ajax/libs/lodash.js/4.17.15/lodash.min.js " > < /脚本>

其他回答

ECMAScript2015选项怎么样?

const a = [5, 5, 5, 2, 2, 2, 2, 2, 9, 4];

const aCount = new Map([...new Set(a)].map(
    x => [x, a.filter(y => y === x).length]
));
aCount.get(5)  // 3
aCount.get(2)  // 5
aCount.get(9)  // 1
aCount.get(4)  // 1

这个例子将输入数组传递给Set构造函数,创建一个唯一值的集合。然后,扩展语法将这些值展开为一个新数组,这样我们就可以调用map并将其转换为一个[value, count]对的二维数组——即如下结构:

Array [
   [5, 3],
   [2, 5],
   [9, 1],
   [4, 1]
]

然后将新数组传递给Map构造函数,得到一个可迭代对象:

Map {
    5 => 3,
    2 => 5,
    9 => 1,
    4 => 1
}

Map对象的伟大之处在于它保留了数据类型——也就是说account .get(5)将返回3,但account .get("5")将返回未定义。它还允许任何值/类型作为键,这意味着该解决方案也适用于对象数组。

函数频率(/*{数组}*/ a){ 返回新地图([…]新组(a)] . map ( X => [X, a.filter(y => y == X).length] )); } 让foo = {value: 'foo'}, Bar = {value: ' Bar '}, Baz ={值:' Baz '}; let aNumbers = [5,5,5,2,2,2,2,2,2,2,2,9,4], aObjects = [foo, bar, foo, foo, baz, bar]; 频率(许多)。forEach (val关键)= > console.log(关键 + ': ' + val)); 频率(aObjects)。forEach((val, key) => console.log(key. log)Value + ': ' + val));

试试这个:

Array.prototype.getItemCount = function(item) {
    var counts = {};
    for(var i = 0; i< this.length; i++) {
        var num = this[i];
        counts[num] = counts[num] ? counts[num]+1 : 1;
    }
    return counts[item] || 0;
}

返回一个可排序的数组:

let array = [5, 5, 5, 2, 2, 2, 2, 2, 9, 4] let reducedArray = array.reduce( (acc, curr, _, arr) => { if (acc.length == 0) acc.push({item: curr, count: 1}) else if (acc.findIndex(f => f.item === curr ) === -1) acc.push({item: curr, count: 1}) else ++acc[acc.findIndex(f => f.item === curr)].count return acc }, []); console.log(reducedArray.sort((a,b) => b.count - a.count )) /* Output: [ { "item": 2, "count": 5 }, { "item": 5, "count": 3 }, { "item": 9, "count": 1 }, { "item": 4, "count": 1 } ] */

你可以使用一个对象来保存结果:

Const arr = [5,5,5,2,2,2,2,2,2,2,2,9,4]; Const counts = {}; (const num of arr) { Counts [num] = Counts [num] ?计数[num] + 1: 1; } console.log(重要); Console.log(计数[5],计数[2],计数[9],计数[4]);

所以,现在你的counts对象可以告诉你一个特定数字的计数是多少:

console.log(counts[5]); // logs '3'

如果您想获取成员数组,只需使用keys()函数即可

keys(counts); // returns ["5", "2", "9", "4"]

根据@adamse和@pmandell的回答(我支持),在ES6中,你可以在一行中完成:

2017年编辑:我使用||来减少代码大小,使其更具可读性。

var =[7, 1、7、2、2、7、3、3、3、7、7、7、7]; 警报(JSON.stringify ( a.reduce ((r, k) = > {[k] = 1 + r [k] | | 1;返回r}, {}) ));


它可以用来计数字符:

var s =“唵嘛呢叭咪吽”; 警报(JSON.stringify ( s.split(”)。Reduce ((a, c)=>{a[c]++?0:a[c]=1;返回a},{}) ));