Javascript 减少对象列表之间比较的复杂性O^2

Javascript 减少对象列表之间比较的复杂性O^2,javascript,arrays,data-structures,Javascript,Arrays,Data Structures,我有两个对象列表: list1 = [{value: 'X'}, {value: 'Y'}, ..., {value: 'Z'}]; list2 = [{value: 'A'}, {value: 'B'}, ..., {value: 'C'}]; 我有一段代码,它检查list2中的值是否在list1中。如果是,代码不起任何作用,如果不是,则应添加到list1(这将创建一个新列表,list3)。这意味着我在两个列表之间进行并集,而不保留重复的值 for (let i = list2.length

我有两个对象列表:

list1 = [{value: 'X'}, {value: 'Y'}, ..., {value: 'Z'}];
list2 = [{value: 'A'}, {value: 'B'}, ..., {value: 'C'}];
我有一段代码,它检查
list2
中的值是否在
list1
中。如果是,代码不起任何作用,如果不是,则应添加到
list1
(这将创建一个新列表,
list3
)。这意味着我在两个列表之间进行并集,而不保留重复的值

for (let i = list2.length-1; i >= 0; i--) {
  let item = list2[i];
  let shared = false;
  for (let j = list1.length-1; j >=0; j--) {
    let childItem = list1[j];
    if (item.value === childItem.value) {
      shared = true;
      break;
    }
  }
  if (!shared) { newValues.push(item); }
}
list3 = list1.concat(newValues);
这很好,但是我想知道我是否可以改进这个O(n*m)

我不确定列表是否总是按默认值排序,但根据我所看到的,列表1和列表2总是按值排序

例如:

var list1 = [{value: 'bar'}, {value: 'baz'}, {value: 'foo'}, {value: 'foz'}];
var list2 = [{value: 'bar'}, {value: 'foo'}, {value: 'test'}, {value: 'testz'}];
var list3 = union(list1, list2);
list3 = [{value: 'bar'}, {value: 'baz'}, {value: 'foo'}, {value: 'foz'}, {value: 'test'}, {value: 'testz'}];

创建一组
list1
的值,并根据集中的值过滤
list2
,然后将其合并到
list1

var list1=[{value:'bar'},{value:'baz'},{value:'foo'},{value:'foz'}];
var list2=[{value:'bar'},{value:'foo'},{value:'test'},{value:'testz'}];
const union=(list1,list2)=>list1.concat(
filter(函数({value}){//filter list2
return!this.has(value);//筛选出值在集合中的项
},新的集合(list1.map(({value}=>value))//list1值的集合
);
const list3=并集(list1,list2);

console.log(列表3)创建一组
list1
的值,并根据集合中的值过滤
list2
,然后将其合并到
list1

var list1=[{value:'bar'},{value:'baz'},{value:'foo'},{value:'foz'}];
var list2=[{value:'bar'},{value:'foo'},{value:'test'},{value:'testz'}];
const union=(list1,list2)=>list1.concat(
filter(函数({value}){//filter list2
return!this.has(value);//筛选出值在集合中的项
},新的集合(list1.map(({value}=>value))//list1值的集合
);
const list3=并集(list1,list2);

console.log(列表3)您可以使用单个循环并将值存储在一个集合中以供以后检查。复杂性:O(n)

var list1=[{value:'X'},{value:'Y'},{value:'C'},{value:'Z'}],
列表2=[{value:'A'},{value:'B'},{value:'C'},{value:'D'}],
list3=list1
.concat(列表2)
.filter((s=>({value})=>!s.has(value)和&s.add(value))(新集合));
console.log(列表3)

.as console wrapper{max height:100%!important;top:0;}
您可以使用单个循环并将值存储在一个集合中,以备以后检查。复杂性:O(n)

var list1=[{value:'X'},{value:'Y'},{value:'C'},{value:'Z'}],
列表2=[{value:'A'},{value:'B'},{value:'C'},{value:'D'}],
list3=list1
.concat(列表2)
.filter((s=>({value})=>!s.has(value)和&s.add(value))(新集合));
console.log(列表3)

.as console wrapper{max height:100%!important;top:0;}
当你说“列表2中的值是否在列表1中”时,你是指,如果有的话,还是全部的值?当你说“列表2中的值是否在列表1中”时,我将添加一个示例来说明你是指,如果有的话,还是全部的话,值?我将添加一个示例来说明问题是关于提高(最坏情况)复杂性的。您的解决方案在这方面做得如何?它实际上在渐近行为方面更好吗?那么,与我发布的代码相比,您的代码有哪些改进?这是因为你没有创建一个临时列表吗?这是因为我在一个循环中没有一个循环,这给了你O(n*m)。创建一个集合是O(2n)。过滤
list2
为O(m)。浓度为O(n+m)。所以总的复杂度是O(3n+2m),我们可以去掉O(n+m)的常数,问题是关于提高(最坏情况)的复杂度。您的解决方案在这方面做得如何?它实际上在渐近行为方面更好吗?那么,与我发布的代码相比,您的代码有哪些改进?这是因为你没有创建一个临时列表吗?这是因为我在一个循环中没有一个循环,这给了你O(n*m)。创建一个集合是O(2n)。过滤
list2
为O(m)。浓度为O(n+m)。所以总的复杂度是O(3n+2m),我们可以去掉O(n+m)的常数。实际上是O(n+m),因为你迭代list1+list2@OriDrori,对于线性复杂度,O(n)足以描述它。实际上,O(n+m)是因为您迭代list1+list2@OriDrori,对于线性复杂度,O(n)足以描述它。