我有一个javascript词典:
{
"a": {
"b": {
"c": null,
"d": null
}
}
}
如何将其转换为JSON对象,我可以指定名称和子属性?有没有优雅的方法呢? JSON对象可以是:
{
name:"a"
children: [{
name:"b",
children: [{
name:"c",
children: null
},{
name:"d",
children: null}]
}]
}
答案 0 :(得分:3)
您可以创建一个递归函数来生成输出:
var x = {
"a": {
"b": {
"c": null,
"d": null
}
}
};
function generate(item, key) {
var result = {
name: key,
children: []
};
for (var _ in item)
result.children.push(generate(item[_], _))
if (result.children.length == 0)
result.children = null;
return (key == undefined) ? result.children : result;
}
console.log(JSON.stringify(generate(x), null, 1));
输出:
[
{
"name": "a",
"children": [
{
"name": "b",
"children": [
{
"name": "c",
"children": null
},
{
"name": "d",
"children": null
}
]
}
]
}
]
上面的generate
函数返回一个列表而不是字典,因为它可能在根级别有多个名称。但是如果我们确定根名称只有一个名称,我们可以像这样生成json:
console.log(JSON.stringify(generate(x)[0], null, 1));
答案 1 :(得分:2)
这是我的解决方案。它与JuniorCompressor的相似。
function generate(obj) {
// Return primitives as-is
if (!(obj instanceof Object)) return obj;
// Loop through object properties and generate array
var result = [];
for (var key in obj) {
result.push({
name: key,
children: generate(obj[key])
});
}
// Return resulting array
return result;
}
如上所述,生成的对象实际上是一个数组(如果原始对象中有多个根级属性)。如果您确实需要生成的对象是仅具有属性名称和值的对象,那么您应该访问结果数组的第一个元素,如下所示:
generate(obj)[0]
答案 2 :(得分:1)
你需要一个递归函数,它为孩子们调用自己。请注意,在您的示例中,只有一个顶级子级(a)。我改为使用顶级“名称”引用实际对象本身名称的假设。如果你想获得与你演示的结果完全相同的结果,从名为'obj'的对象,运行到JSON(obj).children [0]。对于整体功能,请尝试以下内容:
function toJSON(obj, name) {
var subTree = {
name: name,
children: []
};
if (obj !== null && Object.keys(obj).length >= 1) {
for (var child in obj) {
subTree.children.push(toJSON(obj[child], child));
}
} else {
subTree.children = null;
}
return subTree;
}
toJSON(obj)的结果.children [0]:
{
"name": "a",
"children": [{
"name": "b",
"children": [{
"name": "c",
"children": null
},{
"name": "d",
"children": null
}]
}]
}
toJSON(obj,'obj')的结果:
{
"name": "obj",
"children": [{
"name": "a",
"children": [{
"name": "b",
"children": [{
"name": "c",
"children":null
},
{
"name": "d",
"children": null
}]
}]
}]
}
以下是逐行说明:
原始函数只使用了一个参数,而上面的函数有另一个参数'name'。这是因为原版试图找出同一级别中每个级别的名称,我已经意识到这在Javascript中是不可能的。基本上,原件不起作用,并且必须添加额外的参数才能使其工作。但是,为了记录,这里是原始功能:
// THIS FUNCTION DOESN'T WORK. IT'S HERE ONLY FOR HISTORICAL ACCURACY:
function toJSON(obj) {
var subTree = {
name: obj.constructor.name, // This should get the object key
children: []
};
if (Object.keys(obj).length >= 1) { // If there is at least one child
for (var child in obj) {
subTree.children.push(toJSON(obj[child]));
}
} else {
subTree.children = null;
}
return subTree;
}