Как перевернуть древовидную структуру

#javascript #reactjs #tree-traversal

#javascript #reactjs #обход дерева

Вопрос:

У меня XML анализируется как JSON. Я хочу построить дерево компонентов React, пройдя по JSON и вызывая React.createElement каждый узел. Третий аргумент React.createElement — это массив дочерних элементов React . Это означает, что я должен спуститься по дереву до конечных узлов, сначала создать эти элементы React, а затем вернуться к каждой ветви.

Простая рекурсивная итерация по древовидной структуре достаточно проста. Я не уверен, как сказать «хорошо, теперь вы на конечном узле, вернитесь назад». Существуют ли методы для этого?

Пример данных:

 {  
   "section":{  
      "attrs":{  
         "class":"foo",
         "data-foo":"foo"
      },
      "#name":"section",
      "children":[  
         {  
            "attrs":{  
               "class":"region-1"
            },
            "#name":"p",
            "children":[  
               {  
                  "attrs":{  
                     "data-children":"true"
                  },
                  "#name":"span"
               }
            ],
            "span":[  
               {  
                  "attrs":{  
                     "data-children":"true"
                  }
               }
            ]
         },
         {  
            "attrs":{  
               "class":"second"
            },
            "#name":"div"
         }
      ],
      "p":[  
         {  
            "attrs":{  
               "class":"region-1"
            },
            "children":[  
               {  
                  "attrs":{  
                     "data-children":"true"
                  },
                  "#name":"span"
               }
            ],
            "span":[  
               {  
                  "attrs":{  
                     "data-children":"true"
                  }
               }
            ]
         }
      ],
      "div":[  
         {  
            "attrs":{  
               "class":"second"
            }
         }
      ]
   }
}
  

Ответ №1:

В общем, вы можете использовать этот алгоритм. Для наглядности я использовал другие данные. Вместо инструкции используется код, специфичный для вашего приложения console.log . Для надежности я добавил тест на существование дочернего свойства и изменил данные, чтобы проверить его.

 var data = {
    name: 'Parent',
    children: [{
            name: 'Child 1',
            children: [{
                    name: 'Child 1a',
                    children: []
                }, {
                    name: 'Child 1b'
                }
            ]
        }, {
            name: 'Child 2',
            children: [{
                    name: 'Child 2a',
                    children: []
                }, {
                    name: 'Child 2b',
                    children: []
                }
            ]
        }
    ]
};

walk(data);

function walk(node) {
    if (node.children !== undefined) {
        node.children.forEach(function(child) {
            walk(child);
        });
    }

    console.log(node.name);
}  

Ответ №2:

Вы уже решили половину своей проблемы, поскольку знаете, что для итерации по дереву следует использовать рекурсию. Но вместо рендеринга узла, как только вы до него доберетесь, визуализируйте его только в конце рекурсивного стека или после обработки всех дочерних элементов. Это что-то вроде обхода по порядку для двоичных деревьев.

 function iterate(node) {
   if (node.children) {
      node.children.forEach(function (child) {
         iterate(child);
      });
   }

   console.log(node);
}

iterate(section);