J'ai un arbre comme:
let array = [ {"id":1}, {"id":2}, {"id":3}, {"id":4}, {"id":5}, {"id":6}, ]
Comment analyser cet arbre pour pousser chaque nœud
à l'intérieur des enfants
dans un nouveau tableau? Je suppose que je dois l'analyser récursivement. Pouvez-vous m'aider s'il vous plaît?
Le résultat devrait être comme:
{ "nodes": [ { "id":1, "children":[ { "id":3, "children":[ {"id":4, "children":[]}, {"id":5, "children":[{"id":6, "children":[]}]} ] }, {"id":2, "children":[]} ] } ] }
8 Réponses :
Vous pouvez adopter une approche itérative et récursive. Si vous souhaitez obtenir un résultat ordonné, vous pouvez ajouter un tri.
.as-console-wrapper { max-height: 100% !important; top: 0; }
function getValues(array) { return array.reduce((r, { id, children }) => [...r, { id }, ...getValues(children)], []); } var data = { nodes: [{ id: 1, children: [{ id: 3, children: [{ id: 4, children: [] }, { id: 5, children: [{ id: 6, children: [] }] }] }, { id: 2, children: [] }] }] }; console.log(getValues(data.nodes));
Une solution récursive est la voie à suivre:
snip-css
const data = {"nodes":[{"id":1,"children":[{"id":3,"children":[{"id":4,"children":[]},{"id":5,"children":[{"id":6,"children":[]}]}]},{"id":2,"children":[]}]}]}; const getChildren = obj => { let result = []; obj.children.forEach(child => { if (child.children && child.children.length) { result.push({ id: child.id }); result = result.concat(getChildren(child)); } else { result.push({ id: child.id }); } }); return result; }; let res = data.nodes.flatMap(getChildren); console.log(res);
Vous pouvez créer votre propre fonction d'analyse en utilisant la méthode reduction
pour renvoyer tous les nœuds enfants dans une structure de tableau plat.
const tree = {"nodes":[{"id":1,"children":[{"id":3,"children":[{"id":4,"children":[]},{"id":5,"children":[{"id":6,"children":[]}]}]},{"id":2,"children":[]}]}]} function parse(arr) { return arr.reduce((r, e) => { const {children, ...rest} = e; r.push(rest) const childNodes = parse(children); if (childNodes.length) r.push(...childNodes); return r; }, []) } const data = parse(tree.nodes); console.log(data)
Vous pouvez utiliser une fonction pour itérer objet par propriété comme ci-dessous
<script src="https://cdnjs.cloudflare.com/ajax/libs/jquery/3.3.1/jquery.min.js"></script> <div id="output"></div>
var object = { "nodes": [ { "id":1, "children":[ { "id":3, "children":[ {"id":4, "children":[]}, {"id":5, "children":[{"id":6, "children":[]}]} ] }, {"id":2, "children":[]} ] } ] } var result = []; function iterate(obj, stack) { for (var property in obj) { if (obj.hasOwnProperty(property)) { if (typeof obj[property] == "object") { iterate(obj[property], stack + '.' + property); } else { //console.log(property + " " + obj[property]); result.push({[property]: obj[property]}); //$('#output').append($("<div/>").text(stack + '.' + property)) } } } } iterate(object, 'id'); console.log(result)
Une solution récursive de base serait:
var tree = { "nodes": [ { "id":1, "children":[ { "id":3, "children":[ {"id":4, "children":[]}, {"id":5, "children":[{"id":6, "children":[]}]} ] }, {"id":2, "children":[]} ] } ] } function parse(tree, current) { if (current === undefined || current === null) { current = []; } if (Array.isArray(tree)) { tree.forEach(function (node) { if (node.id !== undefined) { current = current.concat([{ id: node.id }]); } if (node.children !== undefined) { current = parse(node.children, current); } }); } return current; } console.log(parse(tree.nodes));
Vous pouvez utiliser une fonction récursive comme ci-dessous:
var nodeObject = { "nodes": [{ "id": 1, "children": [{ "id": 3, "children": [{ "id": 4, "children": [] }, { "id": 5, "children": [{ "id": 6, "children": [] }] } ] }, { "id": 2, "children": [] } ] }] } var ids = []; function getIds(node) { ids.push({ id: node.id }); if (node.children && node.children.length > 0) { node.children.forEach(childNode => getIds(childNode)) } } nodeObject.nodes.forEach(node => getIds(node)) console.log(ids);
Récursivité simple:
data = { "nodes": [ { "id":1, "children":[ { "id":3, "children":[ {"id":4, "children":[]}, {"id":5, "children":[{"id":6, "children":[]}]} ] }, {"id":2, "children":[]} ] } ] } var ids = []; function getIdsFromArray(children) { children.forEach((item) => { if (item.id) ids.push({"id": item.id}); if (item.children && Array.isArray(item.children)) getIdsFromArray(item.children) }) } getIdsFromArray(data.nodes); console.log(ids) //# sourceURL=snippet:///test
Il y a plusieurs façons de faire cela, l'une d'elles est ma solution. Je suis sûr que vous trouverez un meilleur moyen - mais j'ai trouvé la technique Object.entries assez facile.
const myObj = { "nodes": [ { "id":1, "children":[ { "id":3, "children":[ {"id":4, "children":[]}, {"id":5, "children":[{"id":6, "children":[]}]} ] }, {"id":2, "children":[]} ] } ] } let noteArray = Object.entries(myObj.nodes); let pushArray = []; for(const [noteKey, noteValue] of noteArray) { pushArray.push({"id": noteValue.id}); for(const [childKey, childValue] of Object.entries(noteValue.children)) { pushArray.push({"id": childValue.id}); for(const [child2Key, child2Value] of Object.entries(childValue.children)) { pushArray.push({"id": child2Value.id}); } } } console.log(pushArray);
Quelle devrait être la sortie?
Qu'as-tu essayé?