比较2个数组并找到唯一的差异

时间:2015-01-12 18:51:25

标签: javascript arrays json performance knockout.js

假设我们有两个数组

var firstArray = [{"id":1},{"id":3},{"id":5}]
var secondArray = [{"id":1},{"id":2},{"id":3},{"id":4}]
var missingValues = [];

for(var i=0; i < firstArray.length; i++) {
  for(var j=0; j < secondArray.length; j++) {
      if(firstArray[i].id === secondArray[j].id) {
         //do something if I have the same id
      } else {
        missingValues.push(secondArray[j].id); // it should have unique values
      }
  }
}

for(var i = 0; i < missingValues.length; i++) {
  //compare first array and missigValues and remove the same elements
}

我希望得到以下结果。这意味着我需要比较两个数组并删除不在第二个数组中的所有对象,但我还需要保持相同的顺序

firstArray = [{"id":1},{"id":2},{"id":3},{"id":4]

有没有更好的方法呢?因为这些数组内部可能有大量的JSON数据,所以性能更高。 我想尽可能避免多次嵌套。

2 个答案:

答案 0 :(得分:0)

这是一个与我理解的文本描述相匹配的答案,而不是(当前)示例。这可能不正确:

var firstArray = [{"id":1},{"id":3},{"id":5}]
var secondArray = [{"id":1},{"id":2},{"id":3},{"id":4}]

var foundIn = function(list) {
    var ids = list.reduce(function(ids, item) {ids[item.id] = 1; return ids;}, {});
    return function(item) {return !!ids[item.id];};
};

var result = firstArray.filter(foundIn(secondArray)); //=> [{"id":1},{"id":3}]

如果你想从中创建一个完全可重复使用的功能,你可以添加

var onlyFoundIn = function(list1, list2) {return list1.filter(foundIn(list2));};

然后

onlyFoundIn(firstArray, secondArray); //=>  [{"id":1},{"id":3}]

但目前还不清楚这是否真的能满足您的需求。

答案 1 :(得分:0)

你可以使用temp原始数组来防止缓慢的用户域嵌套循环:

var firstArray = [{"id":1},{"id":3},{"id":5}]
var secondArray = [{"id":1},{"id":2},{"id":3},{"id":4}]

var temp=secondArray.map(function(o){return o.id;});

var common=firstArray.filter(function(a){
 return temp.indexOf(a.id)!==-1;
});

JSON.stringify(common) // [{"id":1},{"id":3}]

这种方法假设 id 是建立唯一性的唯一重要值,但它非常快。

如果 id 总是一个数字,否则你永远不会有一个有意义的案例(ex {id:1} vs {id:&#34; 1&#34;},你可以通过使用对象键来建立唯一性,使其更快:

var firstArray = [{"id":1},{"id":3},{"id":5}]
var secondArray = [{"id":1},{"id":2},{"id":3},{"id":4}]

var temp={};
 secondArray.forEach(function(o){temp[o.id]=1; });

var common=firstArray.filter(function(a){
 return temp[a.id]; //note no nested operation at all!
});

JSON.stringify(common) // [{"id":1},{"id":3}]