N-ary Tree Preorder Traversal

Updated on 18 June, 2025
N-ary Tree Preorder Traversal header image

Problem Statement

In this problem, we are dealing with an n-ary tree where each node can have multiple children. The task is to perform a preorder traversal of the tree and return the values of the nodes. Preorder traversal is a type of depth-first traversal where the node is processed before its children.

The n-ary tree is given in a serialized form following the level order traversal. The serialization distinguishes between different levels of children using a null value. Your function will take the root of the tree as input and should output a list representing the preorder traversal of the tree nodes.

Examples

Example 1

Input:

root = [1,null,3,2,4,null,5,6]

Output:

[1,3,5,6,2,4]

Example 2

Input:

root = [1,null,2,3,4,5,null,null,6,7,null,8,null,9,10,null,null,11,null,12,null,13,null,null,14]

Output:

[1,2,3,6,7,11,14,4,8,12,5,9,13,10]

Constraints

  • The number of nodes in the tree is in the range [0, 104].
  • 0 <= Node.val <= 104
  • The height of the n-ary tree is less than or equal to 1000.

Approach and Intuition

The problem of performing a preorder traversal on an n-ary tree can be approached both recursively and iteratively.

  1. Recursive Approach:

    • Start from the root and process the node's value.
    • Recurse over each child of the node and repeat the process. The children are visited in the order they appear.

    The recursive approach aligns intuitively with the definition of preorder traversal, which is to process the node itself followed by recursively processing the children from left to right.

  2. Iterative Approach using a Stack:

    • Initialize a stack with the root node.
    • While the stack is not empty, pop the top node, process it, and push its children onto the stack in reverse order (rightmost child pushed first). This ensures that when popped, the leftmost child is processed before the rightmost child.
    • Continue this process until all nodes have been processed and the stack is empty.

    The use of a stack helps simulate the recursive calls of preorder traversal in an iterative manner. The aim is to process each node and then its children from left to right, which is achieved by controlling the order of nodes placed in the stack.

  • Input Management:
    • The serialization of n-ary trees uses null values to represent boundaries between levels or children groups, important to structure the tree correctly before traversal.

The traversal of an n-ary tree, requires considering all direct children of each node, which makes the preorder traversal particularly well-suited, as it inherently starts processing from the root, moving downwards and leftwards recursively or iteratively, ensuring all nodes are accessed in the required order.

Solutions

  • Java
java
class Solution {
  public List<Integer> getPreorder(Node rootNode) {
    LinkedList<Node> nodeStack = new LinkedList<>();
    LinkedList<Integer> traversalResult = new LinkedList<>();
    if (rootNode == null) {
      return traversalResult;
    }

    nodeStack.add(rootNode);
    while (!nodeStack.isEmpty()) {
      Node currentNode = nodeStack.pollLast();
      traversalResult.add(currentNode.val);
      Collections.reverse(currentNode.children);
      for (Node childNode : currentNode.children) {
        nodeStack.add(childNode);
      }
    }
    return traversalResult;
  }
}

To achieve an N-ary tree preorder traversal in Java, implement the getPreorder function within your Solution class. This function takes in the root of an N-ary tree (Node rootNode) and returns a list of integers representing the traversal order. Here are the steps the code follows to perform the traversal:

  • Start by creating a LinkedList<Node> named nodeStack to help manage the nodes while traversing, and a LinkedList<Integer> named traversalResult to store the traversal sequence.
  • Check if the rootNode is null. If it is, return an empty traversalResult list immediately to signify that no nodes exist to be traversed.
  • Add the rootNode to nodeStack to kickstart the traversal process.
  • Use a while loop to continue the process as long as nodeStack is not empty. Within the loop:
    • Remove the last node from nodeStack using pollLast(), referencing it as currentNode. This node represents the current focus in the traversal.
    • Append currentNode.val (the value of the current node) to traversalResult.
    • Reverse the list of children of the currentNode to ensure they are processed in the order from last to first when added to nodeStack. This step is crucial because LinkedList additions happen at the end, but the traversal needs to process the first child first in a preorder scenario.
    • Iterate through the reversed list of children, adding each child to nodeStack.
  • Return traversalResult which will now contain the values of the nodes in the order they were visited in the preorder traversal.

This implementation ensures that the tree nodes are visited in the correct preorder sequence using a non-recursive approach, leveraging the properties of a stack-based iteration.

Comments

No comments yet.