使用lodash或下划线js查找数组中字符串元素的出现次数

时间:2015-05-21 10:59:53

标签: javascript underscore.js lodash

我有一个以下格式的数组:

var array = [ 
  { id: '555weibo' },
  { id: '578weibo' },
  { id: '111facebook' },
  { id: '123facebook' },
  { id: '145facebookpage' },
  { id: '145facebookpage' },
  { id: '766facebook' },
  { id: '242facebook' },
  { id: '432twitter' },
  { id: '432exing' }
 ];

我需要找到该数组中facebooktwitterxingweibo的出现次数。 例如:

{
  weibo: 2,
  facebook: 6,
  twitter: 1,
  xing: 1
}

我已经找到了解决方案,但似乎没有任何效果。

以下代码未给出预期结果。非常感谢您的帮助。谢谢。

var filtered = _.map(diff, function(value, key) {
   return { id: key, count:value };
});

3 个答案:

答案 0 :(得分:14)

以下是使用lodash的方法:

_.countBy(array, _.flow(
    _.method('id.replace', /^\d+/, ''),
    _.method('replace', /page$/, '')
));
  • countBy()返回一个计数为值的对象。密钥由传入的回调生成,因此您可以在此处解析和操作要计数的密钥。
  • flow()生成一个函数,通常用于回调map()等等。它需要任意数量的函数作为参数。输入通过这些函数中的每一个进行过滤,并返回结果。这是一种强大的回调组合方式,因为它很容易重新排列/添加/删除它的部分。
  • method()返回在给定对象上调用的函数。您想在此处用空字符串替换起始数字。
  • method()在这里做同样的事情,除了它从字符串末尾删除page。注意没有id前缀,因为它只是在它前面传递了函数的结果。

答案 1 :(得分:8)

您必须指定可能的键,因为在初始数组中无法猜测它们。

这是一个解决方案,您不需要任何库:

var filtered = array.reduce(function(m,v){
    for (var k in m) if (~v.id.indexOf(k)) m[k]++;
    return m;
},{facebook:0, weibo:0, twitter:0, xing:0});

Demonstration

答案 2 :(得分:4)

使用下划线:

var services = ['weibo', 'facebook', 'twitter', 'xing'];
var result = _.map(services, function(service){ 
     var length = _.reject(array, function(el){
           return (el.id.indexOf(service) < 0); 
     }).length; 
     return {id: service, count: length};
});