JavaScript 中具有不同键的对象数组的递归函数
Recursive Function In JavaScript for array of objects with different keys
需要 javascript/jquery 中的递归函数用于以下 json 对象。
键"impacted"是每一层的叶节点
键 "child" 可能有任意数量的级别,其中可能有 "impacted" 个节点。
我想将每一层的叶节点("impacted")合并到同一层的子节点("child")。
这意味着任何级别的子节点都应该影响同一级别的数据。
输入
{
"Data": [{
"id": 1745,
"name": "Top Parent",
"parentId": null,
"child": [{
"id": 1746,
"name": "Sub Parent- child to Top Parent",
"parentId": 1745,
"child": [{
"id": 1747,
"name": "child to Sub Parent--One ",
"parentId": 1746
},
{
"id": 1748,
"name": "child to Sub Parent--two",
"parentId": 1746,
"child": [{
"id": 1749,
"name": "Child to two",
"parentId": 1748
}],
"impacted": [{
"id": 2471,
"name": "Leaf of two ",
"network": true
}]
}
],
"impacted": [{
"id": 2470,
"name": "Leaf of Sub Parent-1 ",
"network": true
},
{
"id": 2469,
"name": "Leaf of Sub Parent-1",
"network": true
}
]
}],
"impacted": [{
"id": 2468,
"name": "Leaf Of Top Parent",
"network": true
}]
}]
}
预期输出
{
"Data": [{
"id": 1745,
"name": "Top Parent",
"parentId": null,
"child": [{
"id": 1746,
"name": "Sub Parent- child to Top Parent",
"parentId": 1745,
"child": [{
"id": 1747,
"name": "child to Sub Parent--One ",
"parentId": 1746
},
{
"id": 1748,
"name": "child to Sub Parent--two",
"parentId": 1746,
"child": [{
"id": 1749,
"name": "Child to two",
"parentId": 1748
},
{
"id": 2471,
"name": "Leaf of two ",
"network": true
}
]
},
{
"id": 2470,
"name": "Leaf of Sub Parent-1 ",
"network": true
},
{
"id": 2469,
"name": "Leaf of Sub Parent-1",
"network": true
}
]
},
{
"id": 2468,
"name": "Leaf Of Top Parent",
"network": true
}
]
}]
}
即使我们不从对象中删除 "impacted" 键也可以。但是"impacted"的数据应该合并到同级别的"child"。
我尝试使用以下函数..但在每个级别都得到重复项
repeatLoop(data){
if(data && data.length){
for(var i=0;i<data.length;i++){
if(data[i].child && data[i].child.length && data[i].impacted && data[i].impacted.length){
for(var k=0; k<data[i].impacted.length;k++){
data[i].child.push(data[i].impacted[k])
this.repeatLoop(data[i].child)
}
}
}
}
return data
}
提前致谢
您的代码的主要问题是您在 k
的循环内递归调用该函数,而递归调用根本不依赖于 k
,因此不应调用它在那个内部循环中,但是在之后。
你可以使用这个功能:
class X {
repeatLoop(data) {
if (!Array.isArray(data)) return;
for (var item of data) {
this.repeatLoop(item.child);
if (item.impacted) {
item.child = (item.child || []).concat(item.impacted);
delete item.impacted;
}
}
}
}
// Sample input
var data = {
"Data": [{
"id": 1745,
"name": "Top Parent",
"parentId": null,
"child": [{
"id": 1746,
"name": "Sub Parent- child to Top Parent",
"parentId": 1745,
"child": [{
"id": 1747,
"name": "child to Sub Parent--One ",
"parentId": 1746
},
{
"id": 1748,
"name": "child to Sub Parent--two",
"parentId": 1746,
"child": [{
"id": 1749,
"name": "Child to two",
"parentId": 1748
}],
"impacted": [{
"id": 2471,
"name": "Leaf of two ",
"network": true
}]
}
],
"impacted": [{
"id": 2470,
"name": "Leaf of Sub Parent-1 ",
"network": true
},
{
"id": 2469,
"name": "Leaf of Sub Parent-1",
"network": true
}
]
}],
"impacted": [{
"id": 2468,
"name": "Leaf Of Top Parent",
"network": true
}]
}]
};
// Call function
new X().repeatLoop(data.Data);
// Display mutated data:
console.log(data);
.as-console-wrapper { max-height: 100% !important; top: 0; }
需要 javascript/jquery 中的递归函数用于以下 json 对象。
键"impacted"是每一层的叶节点
键 "child" 可能有任意数量的级别,其中可能有 "impacted" 个节点。
我想将每一层的叶节点("impacted")合并到同一层的子节点("child")。
这意味着任何级别的子节点都应该影响同一级别的数据。
输入
{
"Data": [{
"id": 1745,
"name": "Top Parent",
"parentId": null,
"child": [{
"id": 1746,
"name": "Sub Parent- child to Top Parent",
"parentId": 1745,
"child": [{
"id": 1747,
"name": "child to Sub Parent--One ",
"parentId": 1746
},
{
"id": 1748,
"name": "child to Sub Parent--two",
"parentId": 1746,
"child": [{
"id": 1749,
"name": "Child to two",
"parentId": 1748
}],
"impacted": [{
"id": 2471,
"name": "Leaf of two ",
"network": true
}]
}
],
"impacted": [{
"id": 2470,
"name": "Leaf of Sub Parent-1 ",
"network": true
},
{
"id": 2469,
"name": "Leaf of Sub Parent-1",
"network": true
}
]
}],
"impacted": [{
"id": 2468,
"name": "Leaf Of Top Parent",
"network": true
}]
}]
}
预期输出
{
"Data": [{
"id": 1745,
"name": "Top Parent",
"parentId": null,
"child": [{
"id": 1746,
"name": "Sub Parent- child to Top Parent",
"parentId": 1745,
"child": [{
"id": 1747,
"name": "child to Sub Parent--One ",
"parentId": 1746
},
{
"id": 1748,
"name": "child to Sub Parent--two",
"parentId": 1746,
"child": [{
"id": 1749,
"name": "Child to two",
"parentId": 1748
},
{
"id": 2471,
"name": "Leaf of two ",
"network": true
}
]
},
{
"id": 2470,
"name": "Leaf of Sub Parent-1 ",
"network": true
},
{
"id": 2469,
"name": "Leaf of Sub Parent-1",
"network": true
}
]
},
{
"id": 2468,
"name": "Leaf Of Top Parent",
"network": true
}
]
}]
}
即使我们不从对象中删除 "impacted" 键也可以。但是"impacted"的数据应该合并到同级别的"child"。
我尝试使用以下函数..但在每个级别都得到重复项
repeatLoop(data){
if(data && data.length){
for(var i=0;i<data.length;i++){
if(data[i].child && data[i].child.length && data[i].impacted && data[i].impacted.length){
for(var k=0; k<data[i].impacted.length;k++){
data[i].child.push(data[i].impacted[k])
this.repeatLoop(data[i].child)
}
}
}
}
return data
}
提前致谢
您的代码的主要问题是您在 k
的循环内递归调用该函数,而递归调用根本不依赖于 k
,因此不应调用它在那个内部循环中,但是在之后。
你可以使用这个功能:
class X {
repeatLoop(data) {
if (!Array.isArray(data)) return;
for (var item of data) {
this.repeatLoop(item.child);
if (item.impacted) {
item.child = (item.child || []).concat(item.impacted);
delete item.impacted;
}
}
}
}
// Sample input
var data = {
"Data": [{
"id": 1745,
"name": "Top Parent",
"parentId": null,
"child": [{
"id": 1746,
"name": "Sub Parent- child to Top Parent",
"parentId": 1745,
"child": [{
"id": 1747,
"name": "child to Sub Parent--One ",
"parentId": 1746
},
{
"id": 1748,
"name": "child to Sub Parent--two",
"parentId": 1746,
"child": [{
"id": 1749,
"name": "Child to two",
"parentId": 1748
}],
"impacted": [{
"id": 2471,
"name": "Leaf of two ",
"network": true
}]
}
],
"impacted": [{
"id": 2470,
"name": "Leaf of Sub Parent-1 ",
"network": true
},
{
"id": 2469,
"name": "Leaf of Sub Parent-1",
"network": true
}
]
}],
"impacted": [{
"id": 2468,
"name": "Leaf Of Top Parent",
"network": true
}]
}]
};
// Call function
new X().repeatLoop(data.Data);
// Display mutated data:
console.log(data);
.as-console-wrapper { max-height: 100% !important; top: 0; }