假设我有以下对象数组
[{a:1,b:2,c:4}, {a:3,b:4,c:7}, {a:7,b:10,c:10}, {a:1, b:2,c:4}]
如何选择此数组中的唯一项。我需要比较两个字段(仅a,b,不包括c),我所看到的示例显示的地图仅包含一个字段。
答案 0 :(得分:1)
您可以使用嵌套过滤器,并检查具有相同a
和b
的匹配元素的数量为1:
const input = [{a:1,b:2,c:4}, {a:3,b:4,c:7}, {a:7,b:10,c:10}, {a:1, b:2,c:4}];
const output = input.filter(
({ a, b }) => input.filter(obj => obj.a === a && obj.b === b).length === 1
);
console.log(output);
对于O(N)
复杂度,可以简化为用num_num
索引的对象或类似的对象,然后仅选择其中包含一项的值:
const input = [{a:1,b:2,c:4}, {a:3,b:4,c:7}, {a:7,b:10,c:10}, {a:1, b:2,c:4}];
const inputByAB = input.reduce((accum, obj) => {
const key = `${obj.a}_${obj.b}`;
if (!accum[key]) {
accum[key] = [];
}
accum[key].push(obj);
return accum;
}, {});
const output = Object.values(inputByAB)
.filter(arr => arr.length === 1)
.flat();
console.log(output);
如果您不能使用.flat
,请改为传播concat:
const input = [{a:1,b:2,c:4}, {a:3,b:4,c:7}, {a:7,b:10,c:10}, {a:1, b:2,c:4}];
const inputByAB = input.reduce((accum, obj) => {
const key = `${obj.a}_${obj.b}`;
if (!accum[key]) {
accum[key] = [];
}
accum[key].push(obj);
return accum;
}, {});
const output = [].concat(...
Object.values(inputByAB)
.filter(arr => arr.length === 1)
);
console.log(output);
答案 1 :(得分:1)
对于动态键,请创建一个函数,该函数将代表键的数组和数组字符串作为输入。
创建另一个帮助程序方法,该方法比较两个对象的给定键。
在对象数组上使用filter()
,然后在给定键的当前索引不等于当前对象之前使用every()
元素。
let arr = [{a:1,b:2,c:4}, {a:3,b:4,c:7}, {a:7,b:10,c:10}, {a:1, b:2,c:4}];
function comp(obj1,obj2,keys){
return keys.every(k => obj1[k] === obj2[k]);
}
function getUnique(arr,keys){
return arr.filter((x,i) => arr.slice(0,i).every(a => !comp(a,x,keys)))
}
console.log(getUnique(arr,['a','b']))
答案 2 :(得分:0)
您可以reduce
以Map
作为阵列的数组。将a
和b
属性的组合用作键,以便删除重复项。然后使用Map#values
获取输出
const input = [{a:1,b:2,c:4}, {a:3,b:4,c:7}, {a:7,b:10,c:10}, {a:1, b:2,c:4}],
mapped = input.reduce((map, o) => map.set(o.a + "_" + o.b, o), new Map),
output = Array.from(mapped.values());
console.log(output)