【问题标题】:Fast way to search an array of objects for a matching key/value pair在对象数组中搜索匹配键/值对的快速方法
【发布时间】:2014-05-25 17:57:29
【问题描述】:

我有一个包含大约 950 个对象的数组,每个对象都包含有关足球运动员的基本信息,供我在页面上列出。我正在为此添加搜索功能,其中我检查每个对象中的“名称”键并返回类似的结果。这段代码 sn-p 假设我有一个空数组来存储结果(results = []),并且我正在使用下划线循环 obvs(请参阅:lodash):

_.each(players, function(player, i){

  if(player.name.search(searchString) !== -1){
    results.push(item);
  }

})

这很好用,但需要永远。好的,它实际上需要大约 1 秒,但它或多或少会破坏浏览器,并且在运行时像巧克力蛋糕一样吃掉内存,并且是一个非常缓慢的用户体验。

问题:有没有更好的方法来做到这一点(更好 == 更快)?

如果有帮助,我可以将我的实际数据放在 jsfiddle/jsbin/jswhatever 中。

【问题讨论】:

  • 过滤器可能比每个过滤器运行得稍微快一些,因为它避免了对新集合的额外关闭......该函数体将是“return player.name.search(searchString) !== -1;”此外,如果 searchString 不是 RegExp,则 indexOf() 通常比 search() 快。如果您发布了数据,我们可以在提供建议之前对其进行测试...
  • 我猜想 search() (使用正则表达式)是罪魁祸首,但您应该能够使用每个浏览器内置的分析器自行检查。我经常在 js 中遍历大型(5-20​​k)列表,它通常运行得非常非常快。
  • 好点,@dandavis - 没想过使用 indexOf 代替搜索,但这似乎确实加快了速度!
  • indexOf of 不是最好的搜索方式:jsperf.com/search-indexof-in-read-property

标签: javascript arrays search underscore.js


【解决方案1】:

真的不确定性能,但我想 _.filter 会更适合您的问题。

var results = _.filter(players, function(player){
  return player.name.toLowerCase().indexOf(searchString.toLowerCase()) !== -1;
});

【讨论】:

  • 为什么要将搜索字符串小写 950 次? player.filter(function(player){ return player.name.toLowerCase().indexOf(this) !== -1; },searchString.toLowerCase());避免这种情况
【解决方案2】:
  • 您可以了解search-函数是否比其他“检查”(如 indexOf 或其他)更快或更慢。

  • 您可以做的是让players 数组已经按名称属性排序。然后,您可以按字母顺序浏览数组并跳过与搜索词的第一个字母不匹配的字母范围。 这样你就有了某种索引。

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 2023-01-10
    • 2012-05-20
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2015-07-06
    • 1970-01-01
    相关资源
    最近更新 更多