Можно использовать рекурсивную функцию, которая выполняет итерации по ключам объекта. Затем используйте Object.is для проверки NaN
и null
. Затем проверьте, является ли второй объект типом, приведенным к false
, например 0
, NaN
или null
.
Перечислите ключи обоих объектов и объедините их для проверки отсутствующих ключей в obj1
, а затем выполните итерации.
Если есть разница между одинаковыми значениями ключа, он сохраняет значение object2
и продолжает работу. Если оба значения ключа являются объектными, это значит, что их можно рекурсивно сравнивать.
function diff(obj1, obj2) {
const result = {};
if (Object.is(obj1, obj2)) {
return undefined;
}
if (!obj2 || typeof obj2 !== 'object') {
return obj2;
}
Object.keys(obj1 || {}).concat(Object.keys(obj2 || {})).forEach(key => {
if(obj2[key] !== obj1[key] && !Object.is(obj1[key], obj2[key])) {
result[key] = obj2[key];
}
if(typeof obj2[key] === 'object' && typeof obj1[key] === 'object') {
const value = diff(obj1[key], obj2[key]);
if (value !== undefined) {
result[key] = value;
}
}
});
return result;
}
Код выше лицензирован BSD и может использоваться где угодно.
Тестовая ссылка: https://jsfiddle.net/gartz/vy9zaof2/54/
Важное замечание - это преобразование массивов в объекты и сравнение значений в той же позиции индекса. Есть много других способов сравнения массивов, не охватываемых этой функцией из-за требуемой дополнительной сложности.
РЕДАКТИРОВАТЬ 15/02/2019: этот ответ был изменен, чтобы добавить новый синтаксис ES2017 и исправить варианты использования из комментариев.
Это только начало, я не проверял его, но я начал с рекурсивной функции фильтра или компаратора, измените ее, однако вам нужно получить приоритетные результаты.
function filter(obj1, obj2) {
var result = {};
for(key in obj1) {
if(obj2[key] != obj1[key]) result[key] = obj2[key];
if(typeof obj2[key] == 'array' && typeof obj1[key] == 'array')
result[key] = arguments.callee(obj1[key], obj2[key]);
if(typeof obj2[key] == 'object' && typeof obj1[key] == 'object')
result[key] = arguments.callee(obj1[key], obj2[key]);
}
return result;
}
Тесты: http://jsfiddle.net/gartz/Q3BtG/2/