比对两个数据结构相同的对象并返回两个对象中值不同的键
核心逻辑:将每个有叶子节点的节点保存下来(扁平化过程),因为两个数据结构相同,所以直接排序,对齐两个数组后依次比较,就可以挑出那个改动的key。
因为扁平化可以有深度优先和广度优先两种思路,所以有两个。
BFS版
var getTheLeafProperties = function (obj) {
var result = {} // 保存扁平化后的对象
var queue = [obj] // 队列用于保存每一层的数据
while(queue.length>0){
var currentLevel = queue // 赋值 为了下一步清空队列
queue = [] // 清空队列
for(var i=0;i<currentLevel.length;i++){
var keys = Object.keys(currentLevel[i]) // 获取当前层第i个对象keys
for(var j=0;j<keys.length;j++){
if(typeof currentLevel[i][keys[j]] == 'object'){
// 如果当前层对应的是对象 则入队
queue.push(currentLevel[i][keys[j]])
}else{
// 否则就是叶子结点
result[keys[j]] = currentLevel[i][keys[j]]
}
}
}
}
return result
}
var getTheChangeKey = function (obj1, obj2) {
if(Object.keys(obj1).length == 0 || !obj1 || !obj2)return // 对象为空时就返回undefined
var temp1 = getTheLeafProperties(obj1) // 获取obj1扁平化对象
var temp2 = getTheLeafProperties(obj2) // 获取obj2扁平化对象
console.log(temp1)
console.log(temp2)
var keys = []
// 数组去重 好像去不去都一样
keys.push(...Object.keys(temp1))
keys.push(...Object.keys(temp2))
keys = [...new Set(keys)]
for (var i = 0; i < keys.length; i++) {
if (temp1[keys[i]] != temp2[keys[i]]) {
return keys[i] // 找到立即返回
}
}
return
}
console.log(getTheChangeKey(obj1, obj2))
DFS版(递归实现)
var getTheLeafProperties = function (obj) {
var result = {} // 用于保存扁平化后的对象
var helper = function (obj) {
// 隐含的递归出口是 当对象为空或者不是对象时自动返回
var keys = Object.keys(obj)
for (var i = 0; i < keys.length; i++) {
if (typeof obj[keys[i]] == 'object') {
helper(obj[keys[i]]) // 对这个对象递归调用辅助函数
} else {
result[keys[i]] = obj[keys[i]]
}
}
}
helper(obj) // 初始化递归入口
return result
}
var getTheChangeKey = function (obj1, obj2) {
if (Object.keys(obj1).length == 0 || !obj1 || !obj2) return // 对象为空时就返回undefined
var temp1 = getTheLeafProperties(obj1) // 获取obj1的扁平化对象
var temp2 = getTheLeafProperties(obj2) // 获取obj2的扁平化对象
console.log(temp1)
console.log(temp2)
// 数组去重
var keys = []
keys.push(...Object.keys(temp1))
keys.push(...Object.keys(temp2))
keys = [...new Set(keys)]
for (var i = 0; i < keys.length; i++) {
if (temp1[keys[i]] != temp2[keys[i]]) {
return keys[i]
}
}
return // 若完全一样就返回undefined
}
console.log(getTheChangeKey(obj1, obj2))
测试用例
var time = new Date()
var obj1 = {
a: 1, //
b: {
c: 1, //
d: 2 //
},
e: [1, 2, 3], // 每个都是
f: '123', //
g: {
h: 3, //
i: 5, //
j: {
k: 1, //
l: 14 //
}
}
}
var obj2 = {
a: 1,
b: {
c: 1,
d: 2
},
e: [1, 2, 3],
f: '123',
g: {
h: 3,
i: 5,
j: {
k: 1,
l: 2 // 改动了这里
}
}
}