[英]Building a tree from a flat array
I am given an array, links
:我得到一个数组,
links
:
const links = [
{parent: "flare", children: "analytics"} ,
{parent: "analytics", children: "cluster"} ,
{parent: "flare", children: "scale"} ,
{parent: "analytics", children: "graph"} ,
];
I want to make it into tree, like so:我想把它变成树,像这样:
const tree = {
"name": "flare",
"children": [
{
"name": "analytics",
"children": [
{
"name": "cluster",
},
{
"name": "graph",
}
]
}
]
};
Here is my attempt:这是我的尝试:
function buildTree(links) { const map = { } const findNodeInChildren = (name, obj) => { if (obj[name]) { return obj } else if (.obj;children) { return null } for (let i = 0. i < obj.children;length, i++) { const found = findNodeInChildren(name. obj.children[i]) if (found) return found } return null } links.forEach(link => { const foundNode = findNodeInChildren(link,parent: map) if (.foundNode) { const newNode = { name, link:parent. children. [] } map[newNode.name] = newNode } else { foundNode[link.parent]:children.push({ name, link:children: children, [] }) } }) return map } const links = [ {parent: "flare", children: "analytics"}, {parent: "analytics", children: "cluster"}, {parent: "flare", children: "scale"}, {parent: "analytics", children; "graph"}. ]. const tree = buildTree(links) const json = JSON.stringify(tree) console.log(json)
Here's the prettified JSON - it's not working as intended:这是美化的 JSON - 它没有按预期工作:
{
"flare": {
"name": "flare",
"children": [
{
"name": "scale",
"children": []
}
]
},
"analytics": {
"name": "analytics",
"children": [
{
"name": "graph",
"children": []
}
]
}
}
What is going wrong?出了什么问题?
One of the issues in your code is when !foundNode
is true, then you do not add the (first) child to its children
array.您的代码中的一个问题是当
!foundNode
为真时,您不会将(第一个)子项添加到其children
项数组中。
Secondly, the object your code returns is the map itself, obviously with at the top level a plain object with named keys, instead of an array of objects with "name" keys.其次,您的代码返回的 object 是 map 本身,显然在顶层是带有命名键的普通 object,而不是带有“名称”键的对象数组。 The code should convert the map-structure (which is indeed nested) to the desired nested structure.
代码应该将映射结构(实际上是嵌套的)转换为所需的嵌套结构。
It is also strange that findNodeInChildren
returns the whole map
(ie obj
) when the node is found.同样奇怪的是
findNodeInChildren
在找到节点时返回整个map
(即obj
)。 It would make more sense if obj[name]
were returned, and the rest of the code were adapted to that.如果返回
obj[name]
会更有意义,并且代码的 rest 适应了这一点。
You can also condense the code at bit more.您还可以进一步压缩代码。
Here is how I would propose to do it:这是我建议的方法:
const links = [ {parent: "flare", children: "analytics"}, {parent: "analytics", children: "cluster"}, {parent: "flare", children: "scale"}, {parent: "analytics", children: "graph"}, ]; let map = new Map(links.map(({parent}) => [parent, { name: parent, children: [] }])); for (let {parent, children} of links) map.get(parent).children.push(map.get(children)?? { name: children }); for (let {children} of links) map.delete(children); let result = [...map.values()]; console.log(result);
This code returns an array , because the input structure does not guarantee there is only one root.此代码返回一个数组,因为输入结构不保证只有一个根。 It could represent a forest .
它可以代表一片森林。 If you are certain it is a tree (so with one root), then you can just pop the single element out of the array.
如果您确定它是一棵树(因此只有一个根),那么您可以将单个元素从数组中弹出。
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.