2
votes

Comment traiter l'arbre JSON?

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":[]}
      ]
    }
  ]
}


2 commentaires

Quelle devrait être la sortie?


Qu'as-tu essayé?


8 Réponses :


3
votes

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));


0 commentaires

0
votes

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);


0 commentaires

1
votes

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)


0 commentaires

0
votes

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)


0 commentaires

0
votes

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));


0 commentaires

1
votes

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);


0 commentaires

0
votes

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


0 commentaires

1
votes

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);


0 commentaires