jQuery使用多个关键对象拼接inArray

时间:2013-04-05 16:48:20

标签: javascript jquery

Javascript newbie here -

我有以下数组:

var group = ({ 
        one: value1,
        two: value2,
        three: value3
    });

我想检查数组“group”是否为“groupsArray”的一部分,如果没有则添加它,如果有则将其删除。

var groupLocate = $.inArray(group, groupsArray);
if(groupLocate ==-1){
        groupsArray.push(group);
        } else {
        groupsArray.splice($.inArray(group, groupsArray),1);
        }

此方法适用于单值数组。不幸的是,在这种情况下我无法使用三个键和值来工作,因为groupLocate总是返回-1。

我做错了什么?

感谢。

1 个答案:

答案 0 :(得分:2)

首先,它有助于理解为什么$.inArray()不起作用。让我们尝试一个更简单的案例。将其粘贴到浏览器中的JavaScript控制台上,加载jQuery的页面(例如我们所在的页面)并运行它:

var object = { a: 1 };
var array = [ { a: 1 } ];
console.log( '$.inArray: ', $.inArray( object, array ) );

(注意术语:您的group变量是Object,而不是Array。)

现在看起来object在数组中,对吗?为什么打印-1呢?试试这个:

console.log( object );
console.log( array[0] );

他们看起来一样。怎么样:

console.log( '== or === works? ', object == array[0], object === array[0] );

甚至更简单:

console.log( 'Does {a:1} == {a:1}? ', {a:1} == {a:1} );
console.log( 'What about {} == {}? ', {} == {} );

全部打印false

这是因为碰巧具有相同内容的两个对象仍然是两个独立的对象,当您使用=====来比较两个对象时,您实际上正在测试它们是否都是引用同一个对象。两个不同的对象永远不会相等,即使它们包含完全相同的内容。

$.inArray()就像使用===运算符来比较两个对象一样 - 它不会在数组中找到对象,除非它是相同的对象,而不仅仅是具有相同内容的对象。

了解这一点,是否表明有任何可能的方法来解决问题?有几种方法可以编写自己的代码来搜索数组中的对象,或者您可能会发现使用诸如Underscore.js这样的库有用,它有许多有用的数组和对象方法。

例如,您可以使用_.findWhere( groupsArray, group )查找第一个匹配项 - 但需要注意的是它只会比较group对象中的属性。例如,如果group{a:1},则它会匹配groupsArray数组中{a:1,b:2}的对象。

如果您需要完全匹配,可以结合使用Underscore的_.find()_.isEqual()方法:

var index = _.find( groupsArray, function( element ) {
    return  _.isEqual( element, group );
});

现在最后要注意的一件事。将group对象推送到groupsArray数组的代码 - 您知道推送实际的group对象本身。它不会在数组中复制它,它是对同一个对象的引用。 (具有讽刺意味的是,这意味着在数组中查找group的原始代码实际上可以用于您自己将相同的group对象推送到数组上的情况。)

如果要确保groupsArray中的元素都是它们自己的独立对象,而不是对代码中浮动的另一个对象的引用,则可以使用另一个Underscore方法来执行浅层复制:< / p>

groupsArray.push( _.clone(group) );

如果group有任何嵌套对象,则不会复制它们。 (我在Underscore中没有看到深层复制功能,但如果需要,可以写一个。)