我试图尽可能有效地找到任意数量的对象之间的交集。这些对象都包含其他子对象,每个子对象都存储在父对象的唯一键下。为了我的目的,可以安全地假设当将对象1上的子对象a与对象2上的子对象进行比较时,内容是相同的,所以我不在乎是否覆盖了另一个。到目前为止,这是我正在使用的解决方案,但我担心它不够有效:
function intersectObjects(...objects){
/*NOTE: This function will overwrite values on duplicate keys*/
var returnObj; //temp variable to store the return value
objects.forEach((obj, i) => {
//on the first loop store my object
if (i == 0) returnObj = obj;
else {
//Get an array of all properties currently being returned
const returnProps = Object.getOwnPropertyNames(returnObj);
//Loop over the properties array
returnProps.forEach((propKey, j) => {
//If the current property does not exist on the return object
//Then delete the property on the return object
if(!obj[returnProps[j]]) delete returnObj[returnProps[j]];
});
}
});
return returnObj;
}
对此有更有效的解决方案吗?是否有一个库来处理这个功能并且有效地运行它?是否有一个我不知道的功能?任何这些问题的答案将不胜感激。
答案 0 :(得分:1)
你可以使用这个ES6函数,它不会改变任何输入对象,但会返回一个新的:
function intersectObjects(...objects) {
return !objects.length ? {}
: Object.assign(...Object.keys(objects[0]).filter(
key => objects.every( o => key in o )
).map( key => ({ [key]: objects[0][key]}) ));
}
// Sample run
var data = [
{ a: 1, b: 2, c: 3, d: 4, e: 5},
{ b: 2, c: 3, d: 4, e: 5, f: 6},
{ a: 1, b: 2, d: 4, e: 5},
{ a: 1, b: 2, c: 3, d: 4, e: 5, f: 6, g: 7}
];
var result = intersectObjects(...data);
console.log(result);

.as-console-wrapper { max-height: 100% !important; top: 0; }

请注意,在对象上执行delete
是一项代价高昂的操作,并且削弱了引擎可以寻求和应用的优化。
答案 1 :(得分:0)
如果没有测试样本数据,我无法告诉您这是否适合您的需求,但您可以试一试。
function intersectObjects(...objects) {
return Object.assign.apply(null, objects);
}