打字稿:如何在2个对象之间找到匹配的属性

时间:2019-04-05 19:25:57

标签: typescript search properties

我有2个具有这样的嵌套属性的对象:

const obj1 = {
   prop1: {
     val1: 10,
     val2: 11,
     val3: 12,
   },
   prop2: {
     val1: 10,
     diff1: true,
   },
   prop4: {
     text1: 't1',
     text99: 't1',
   }
};
const obj2 = {
   prop1: {
     val99: 1000,
     val2: 1100,
     val33: 1200,
   },
   anotherOne: {
     val1: 1000,
     diff1: false,
   },
   prop4: {
     check: true,
     text1: 't100',
     text99: 't100',
   }
};

如何找到两个对象之间共有的属性?即对于上面的示例,我有兴趣获得以下信息:

const propertiesInObj1AndObj2 = {
   prop1: {
     val2: '',
   },
   prop4: {
     text1: '',
     text99: '',
   }
};

有没有一种很好的方法来获得此结果?还是我需要手动遍历obj1中找到的每个属性并在obj2中搜索相同的属性以查看是否存在匹配项?

2 个答案:

答案 0 :(得分:1)

O(n2)

  

工作示例https://stackblitz.com/edit/typescript-2uminr

const obj1 = {
   prop1: {
     val1: 10,
     val2: 11,
     val3: 12,
   },
   prop2: {
     val1: 10,
     diff1: true,
   },
   prop4: {
     text1: 't1',
     text99: 't1',
   }
};
const obj2 = {
   prop1: {
     val99: 1000,
     val2: 1100,
     val33: 1200,
   },
   anotherOne: {
     val1: 1000,
     diff1: false,
   },
   prop4: {
     check: true,
     text1: 't100',
     text99: 't100',
   }
};


const duplicate: any[] = [];

Object.keys(obj1).map( ob1 => {
  Object.keys(obj2).map( ob2 => {
    if (match(ob1, ob2)) { duplicate.push(ob2) } 
  });
});

function match(key1: string, key2: string) {
  return (key1 === key2) ? true : false;
}

console.log(duplicate)

答案 1 :(得分:1)

我认为这确实取决于您的用例...您是否需要支持数组?如果两个属性都存在但类型不同怎么办?等等等等

您将不得不遍历至少一个对象的键,但是由于您只对键集的交集感兴趣,因此不需要遍历这两个对象。当然,该函数必须是递归的。

这是一种可能的实现,也可以在类型级别上使用:

type SameKeyThing<T, U> =
    [T, U] extends [object, object] ?
    { [K in (keyof T) & (keyof U)]: SameKeyThing<T[K], U[K]> } : "";

function sameKeyThing<T, U, S=SameKeyThing<T, U>>(x: T, y: U): { [K in keyof S]: S[K] };
function sameKeyThing(x: any, y: any) {
    if ((typeof x !== "object") || (typeof y !== "object")) return "";
    const ret: any = {};
    for (let k in x) {
        if (k in y) {
            ret[k] = sameKeyThing(x[k], y[k]);
        }
    }
    return ret;
}
const propertiesInObj1AndObj2 = sameKeyThing(obj1, obj2);
// inferred as type { prop1: { val2: ""; }; prop4: { text1: ""; text99: ""; }; }
console.log(propertiesInObj1AndObj2);

这对于您的示例来说效果很好,但是如果您向其抛出边缘情况(例如那些数组),则可能会有奇怪的行为。无论如何,希望这能给您一些想法。祝你好运!