2010-12-01 60 views
2

我有一个特殊的问题,我正在处理。我会开始模糊,如果有人需要更多的细节,我可以提供有关该项目的背景知识。jQuery/javascript查找列表中的值

我具有选定的ID(从一个复选框选择的):161

我有像这样的ID的许多行:

["161", "165", "573", "190", "150", "283"] // this one would be it 
["160", "311", "793", "309", "301"] 
["161", "165", "395", "306"] // this one would be it 
["160", "311", "668", "191", "216", "301"] 

我需要识别出的ID的上面的行,哪些人的ID已被选中。这并不难,我可以遍历每行ID(循环遍历实际数组),并执行thisIDList[i] == selectedID。当已经选择了多个ID我有

问题是:["161", "306"]

现在我需要通过行循环和识别哪些行具有所选ID的两个

["161", "165", "573", "190", "150", "283"] // wouldn't be it 
["160", "311", "793", "309", "301"] 
["161", "165", "395", "306"] // this one would be it 
["160", "311", "668", "191", "216", "301"] 

等等。可以选择1到5或6个ID:["161", "306", "216", "668"]

有人能指出我的方向吗?我认为这基本上是比较喜欢的两个列表,其中A组名单所列每个项目需要在列表B.对发现


编辑

我要补充该行能够包含在没有发现其他ID选定的列表。所以,如果所选的ID是["161", "306"],然后["161", "165", "395", "306"]将是一个匹配的是,尽管它包含了165和395.


编辑

要更新,给多一点信息。我有单选按钮的列表:

<input type="checkbox" name="filter" value="301" /> 
<input type="checkbox" name="filter" value="161" /> 
<input type="checkbox" name="filter" value="573" /> 
<input type="checkbox" name="filter" value="190" /> 

我有一个无序列表,每个列表具有数据属性(我使用所述元数据插件):

<ul> 
    <li data="{attrID: '160,197,161,194,195,190,162' }">Lorem Ipsum</li> 
</ul> 

当点击单选按钮:

// set the selected IDs 
selectedIds = []; 
$("input[name=filter]:checked").each(function(){ 
    selectedIds.push(this.value); 
}); 

// loop through each list     
$('ul li').each(function() { 

    // get and set the metadata for the attrID key 
    meta = $(this).metadata(); 
    idList = meta.attrID; 

    // find out if the selected IDs are found in this idList 
    var isMatch = matches(selectedIds,idList); 

    console.log(isMatch); 

    // my plan was to do this 
    if(isMatch){ 
     // do something with this list item 
    } 


}); 

回答

3

它使用inArray功能从jQuery的。它返回一个数组,其中包含包含目标集所有元素的集合的索引。如果你的套件相对较小,就像在你的例子中那样,它应该足够快。根据您的数据

function matches(target, sets) 
{ 
    var matches= []; 
    for (var i = 0, setsLen = sets.length; i < setsLen; ++i) { 
     if (isSubset(target,sets[i])) { 
      matches.push(i); 
     } 
    } 
    return matches; 
} 

function isSubset(target, set) 
{ 
    for (var j = 0, targetLen = target.length; j < targetLen; ++j) { 
     if ($.inArray(target[j], set) < 0) { 
      return false; 
     } 
    } 
    return true; 
} 

一个小的测试脚本:

$(function(){ 
    var sets = [ 
        ["161", "165", "573", "190", "150", "283"], 
        ["160", "311", "793", "309", "301"], 
        ["161", "165", "395", "306"], 
        ["160", "311", "668", "191", "216", "301"] 
    ]; 

    alert(matches([ "161" ], sets)); 
    alert(matches([ "161","306" ], sets)); 
}); 

编辑:我更新根据您的补充我的榜样。我想你只需要使用isSubset函数。我将把剩下的答案留给上下文。

0

如果您是通过对每个数组进行排序而开始的,则只需遍历每个列表一次。

0

如何在找到X个ID之一时递增变量,并在达到最终结果时将其与选定ID的总数进行匹配。如果找到4个中的4个,则匹配

2

这样做的最快和最可重用的方法是创建isSubset函数。你甚至不依赖于jQuery!

function isSubset(largeSet, smallSet){ 

    for(var i=0; i<smallSet.length; i++){ 
     if(largeSet.indexOf(smallSet[i]) == -1){ 
      //not found. 
      return false; 
     } 
    } 

    return true; 
} 

现在遍历所有的ID列表阵列并通过您选择的ID阵列:

isSubset(idList, selectedIds); 

如果上述返回true,你已经确定了有效列表!

=============

编辑:感谢埃里克,您指出的indexOf带一个漏洞()。

下面的代码应该可以解决所有的浏览器这个问题:

if (!Array.indexOf) { 
    Array.prototype.indexOf = function (obj, start) { 
    for (var i = (start || 0); i < this.length; i++) { 
     if (this[i] == obj) { 
     return i; 
     } 
    } 
    return -1; 
    } 
} 
+3

请谨慎[支持IE中的`Array.indexOf()`](http://stellapower.net/content/javascript-support-and-arrayindexof-ie)... – Eric 2010-12-01 20:41:18

+0

谢谢!现在试试这个... – jyoseph 2010-12-01 21:09:55