I have an array of object that look this,
const data = [
{
"key": "group1",
"name": "groupname1",
"total": 65,
"available": 34,
"children": [
{
"key": "cat1",
"name": "category1",
"total": 5,
"available": 2,
"children": []
},
{
"key": "cat2",
"name": "category2",
"total": 60,
"available": 32,
"children": [
{
"key": "cat3",
"name": "category3",
"total": 15,
"available": 12,
"children": []
},
{
"key": "cat6",
"name": "category6",
"total": 55,
"available": 20,
"children": []
}
]
}
]
},
{
"key": "group2",
"name": "groupname2",
"total": 75,
"available": 47,
"children": [
{
"key": "cat4",
"name": "category4",
"total": 25,
"available": 22,
"children": []
},
{
"key": "cat5",
"name": "category5",
"total": 50,
"available": 25,
"children": []
}
]
}
]
key property at each level is unique across the entire tree. When I pass in key as a paremeter and this array to a functon, it should increment the available
value at the matching key level and this increment should go all the way upto root.So basically when I pass incrementRecursively(data, "cat3"), the output should look like,
[
{
"key": "group1",
"name": "groupname1",
"total": 65,
"available": 35,
"children": [
{
"key": "cat1",
"name": "category1",
"total": 5,
"available": 2,
"children": []
},
{
"key": "cat2",
"name": "category2",
"total": 60,
"available": 33,
"children": [
{
"key": "cat3",
"name": "category3",
"total": 15,
"available": 13,
"children": []
},
{
"key": "cat6",
"name": "category6",
"total": 55,
"available": 20,
"children": []
}
]
}
]
},
{
"key": "group2",
"name": "groupname2",
"total": 75,
"available": 47,
"children": [
{
"key": "cat4",
"name": "category4",
"total": 25,
"available": 22,
"children": []
},
{
"key": "cat5",
"name": "category5",
"total": 50,
"available": 25,
"children": []
}
]
}
]
How can I track the parent and update the increments all the way to the root node? Code I tried that doesnt work
function increment(nodes, key, depth = 0) {
for (let n of nodes) {
const nodeOwnKeyMatches = n.key === key;
const nodeChildsKeyMatches = increment(n.children, key, depth + 1);
if (!nodeOwnKeyMatches && !nodeChildsKeyMatches) continue;
if (nodeOwnKeyMatches) n.available++;
}
}
2
Answers
This is how I’d do it: For each node, check if there is a key match or if one of its children is a key match (recursively). If so, increment the
available
property of the node and returntrue
to indicate that a match was found.As per the comment below, to prevent top-level nodes being incremented as a result of descendent key matches:
The result is also possible to achieve with a help of Map and a little addition to the structure of the original tree.