使用下划线或jquery的真值函数在js数组中的IndexOf元素

时间:2011-11-01 15:48:16

标签: javascript jquery underscore.js

我需要与Underscore的find基本相同的功能,但结果是元素的索引(而不是元素本身)。

据我所知,Underscore的indexOf寻找一个值而不是一个函数。 jQuery的inArray函数也存在同样的问题。

我想出了以下实现,但我不确定它是最有效的:

function myIndexOf(arr, filter) {
  var index;
  $.each(arr, function (i, elt) { if (filter(elt)) { index=i; return false; } });
  return index;
}

5 个答案:

答案 0 :(得分:10)

<{3}}和Lo-Dash提供了{p> _.findIndex

var characters = [
  { 'name': 'barney',  'age': 36, 'blocked': false },
  { 'name': 'fred',    'age': 40, 'blocked': true },
  { 'name': 'pebbles', 'age': 1,  'blocked': false }
];

_.findIndex(characters, function(chr) {
  return chr.age < 20;
});
// → 2

_.findIndex(characters, { 'age': 36 });
// → 0

_.findIndex(characters, { 'name': 'dino' });
// → -1 (not found)

答案 1 :(得分:5)

这是一个简单的实现:

function find(collection, filter) {
    for (var i = 0; i < collection.length; i++) {
        if(filter(collection[i], i, collection)) return i;
    }
    return -1;
}

它适用于任何具有length属性的可索引对象,您可以传递filter(element, index, collection)形式的复杂过滤函数(可选参数)。

答案 2 :(得分:5)

Underscore使用以下实现:

_.find = function(obj, iterator, context) {
    var result;
    _.any(obj, function(value, index, list) {
        if(iterator.call(context, value, index, list)) {
            result = value;
            return true;
        }
    });
    return result;
}

这反过来调用_.any,调用_.each,调用Array.prototype.forEach。效率并不完全是游戏的名称。它更多的是实用性。

如果你知道你正在处理一个数组或类似数组的对象,你可以使用@ Thor84no的解决方案,只需循环遍历数组,直到满足你的过滤条件。如果没有,你也可能正在处理对象,我只需将_.find重写为_.findIndex并使用result = index;

答案 3 :(得分:3)

您可以使用局部变量来实现:

var idx = 0; 
var match = _.detect(my_list, function(itm){
    return itm.something == some_test_value || ++idx == my_list.length && (idx = -1);
}

中提琴。你得到了索引和匹配值。如果迭代器到达结尾,则索引变为-1,如果匹配,则会在该索引上短路。

答案 4 :(得分:2)

自己进行for循环会更有效,并且在找到索引后使用break;(或return)离开循环。

for (var i = 0; i < arr.length; i++) {
    if (filter(arr[i])) {
        return i;
    }
}