我想知道是否可以用点表示法动态生成带有字符串数组的对象。我想从CSV文件动态构建JSON对象。目标是将CSV构建为JSON,然后过滤属性并创建一个新的JSON对象。
所以我想传递类似的内容..
var obj = {};
var keyArray = ['meta', 'logos', 'warranty', 'specs', 'specs.engine', 'specs.engine.hp', 'specs.engine.rpm', 'specs.engine.manufacturer'];
最终结果将是这样的......
obj = {
meta: {
},
logos: {
},
specs: {
engine: {
hp: {
}
}
}
}
这是主要功能
function addObjectsByKey(obj, keyArray) {
for (var key in keyArray) {
// If keyword is not in object notation
if (!(keyArray[key].match(/\./))) {
// If the object property is not set, set it
if (!(obj[keyArray[key]])) {
obj[keyArray[key]] = {};
}
} else {
// Split array element (in dot notation) into an array of strings
// These strings will be object properties
var pathAsArray = keyArray[key].split('.');
var path = null;
for (var k in pathAsArray) {
if (path == null) {
obj[pathAsArray[k]] = {};
path = pathAsArray[k];
} else {
obj[path][pathAsArray[k]] = {};
path += '.' + pathAsArray[k];
}
}
// throw Error('end');
}
}
// return obj;
}
答案 0 :(得分:2)
您可以使用forEach
循环,在内部可以拆分.
上的每个元素,然后使用reduce
方法构建嵌套对象。
var keyArray = ['meta', 'logos', 'warranty', 'specs', 'specs.engine', 'specs.engine.hp', 'specs.engine.rpm', 'specs.engine.manufacturer'];
const result = {}
keyArray.forEach(key => {
// Loop array of keys
// Split each key with . and use reduce on that
// In each iteration of reduce return r[e] which is going to be value if property exists
// or new object if it doesn't
// This way you can go to any object depth as long as keys match existing keys in object.
key.split('.').reduce((r, e) => r[e] = (r[e] || {}), result)
})
console.log(result)
这是使用for
循环的另一种方法,它将返回相同的结果。
var keyArray = ['meta', 'logos', 'warranty', 'specs', 'specs.engine', 'specs.engine.hp', 'specs.engine.rpm', 'specs.engine.manufacturer' ];
const result = {}
for(var i = 0; i < keyArray.length; i++) {
const keys = keyArray[i].split('.');
let ref = result;
for(var j = 0; j < keys.length; j++) {
const key = keys[j];
if(!ref[key]) ref[key] = {}
ref = ref[key]
}
}
console.log(result)
答案 1 :(得分:1)
您可以使用函数reduce
和嵌套forEach
来构建路径。
reduce
将累积嵌套操作。forEach
将根据以点分隔的当前路径构建对象及其子对象。
let keyArray = ['meta', 'logos', 'warranty', 'specs', 'specs.engine', 'specs.engine.hp', 'specs.engine.rpm', 'specs.engine.manufacturer'],
newObj = keyArray.reduce((accum, path) => {
let previous = accum;
path.split('.').forEach(key => {
if (previous[key]) previous = previous[key];
else previous = previous[key] = {};
});
return accum;
}, {});
console.log(newObj);
.as-console-wrapper { max-height: 100% !important; top: 0; }