格式转换
题目描述
给定一个“扁平”字典对象,其键是以点分割的。请实现一个函数,将其转换为”嵌套的”字典对象。
示例
输入:{'a':1,'b.a':2,'b.b':3,'c.d.e':4,'c.d'f':5}
输出:{
'a':1,
'b':{
'a':2,
'b':'3'
},
'c':{
'd':{
'e':4,
'f':5
}
}
}
解题思路
- 首先将原对象进行转换,以原对象的值为键,原对象的键用
.
切割后得到的数组为值,以示例中的对象为例,得到转换后的对象 tempObj,如下图所示:
- 利用递归将 tempObj 还原成嵌套的对象:
- 遍历 tempObj 中所有键值对,对每一个键值对调用 createObj 函数将其添加到最终的 res 中去
- createObj 接受四个参数 obj-要添加的对象,arr-要添加的记录嵌套关系的 key 数组,index-当前处理到的 key 索引,val-要添加的值
- 当 index=arr.length-1 时,表示已经处理到最深一层的属性,因此可以直接给 obj 添加相应的属性和值
- 当 arr[index]这个属性在 obj 中不存在的话,说明这个属性是多重嵌套中间的属性,可以初始化这个属性,然后递归调用 createObj
- 当 arr[index]这个属性存在的时候,直接进行下一次递归调用
代码
function convertObj(obj) {
const tempObj = {};
for (let key in obj) {
tempObj[obj[key]] = key.split(".");
}
const res = {};
for (let key in tempObj) {
createObj(res, tempObj[key], 0, key);
}
return res;
}
function createObj(obj, arr, index, val) {
if (index === arr.length - 1) {
obj[arr[index]] = val;
} else if (!obj[arr[index]]) {
obj[arr[index]] = {};
const i = index + 1;
createObj(obj[arr[index]], arr, i, val);
} else if (obj[arr[index]]) {
const i = index + 1;
createObj(obj[arr[index]], arr, i, val);
}
}
测试结果:
const obj = {
a: 1,
"b.a": 2,
"b.b": 3,
"c.d.e": 4,
"c.d.f": 5,
};
console.log(convertObj(obj));
// { a: '1', b: { a: '2', b: '3' }, c: { d: { e: '4', f: '5' } } }