Friday, November 22, 2024
Google search engine
HomeData Modelling & AITree Traversal Techniques – Data Structure and Algorithm Tutorials

Tree Traversal Techniques – Data Structure and Algorithm Tutorials

Unlike linear data structures (Array, Linked List, Queues, Stacks, etc) which have only one logical way to traverse them, trees can be traversed in different ways. 

A Tree Data Structure can be traversed in following ways:

  1. Depth First Search or DFS
    1. Inorder Traversal
    2. Preorder Traversal
    3. Postorder Traversal
  2. Level Order Traversal or Breadth First Search or BFS
  3. Boundary Traversal
  4. Diagonal Traversal
Tree Traversal

Tree Traversal

Inorder Traversal:

Algorithm Inorder(tree)

  1. Traverse the left subtree, i.e., call Inorder(left->subtree)
  2. Visit the root.
  3. Traverse the right subtree, i.e., call Inorder(right->subtree)

Uses of Inorder Traversal:

In the case of binary search trees (BST), Inorder traversal gives nodes in non-decreasing order. To get nodes of BST in non-increasing order, a variation of Inorder traversal where Inorder traversal is reversed can be used.

Code implementation of Inorder traversal.

C




// C program for different tree traversals
#include <stdio.h>
#include <stdlib.h>
 
// A binary tree node has data, pointer to left child
// and a pointer to right child
struct node {
    int data;
    struct node* left;
    struct node* right;
};
 
// Helper function that allocates a new node with the
// given data and NULL left and right pointers.
struct node* newNode(int data)
{
    struct node* node
        = (struct node*)malloc(sizeof(struct node));
    node->data = data;
    node->left = NULL;
    node->right = NULL;
 
    return (node);
}
 
// Given a binary tree, print its nodes in inorder
void printInorder(struct node* node)
{
    if (node == NULL)
        return;
 
    // First recur on left child
    printInorder(node->left);
 
    // Then print the data of node
    printf("%d ", node->data);
 
    // Now recur on right child
    printInorder(node->right);
}
 
// Driver code
int main()
{
    struct node* root = newNode(1);
    root->left = newNode(2);
    root->right = newNode(3);
    root->left->left = newNode(4);
    root->left->right = newNode(5);
 
    // Function call
    printf("Inorder traversal of binary tree is \n");
    printInorder(root);
 
    getchar();
    return 0;
}


C++




// C++ program for different tree traversals
#include <bits/stdc++.h>
using namespace std;
 
// A binary tree node has data, pointer to left child
// and a pointer to right child
struct Node {
    int data;
    struct Node *left, *right;
};
 
// Utility function to create a new tree node
Node* newNode(int data)
{
    Node* temp = new Node;
    temp->data = data;
    temp->left = temp->right = NULL;
    return temp;
}
 
// Given a binary tree, print its nodes in inorder
void printInorder(struct Node* node)
{
    if (node == NULL)
        return;
 
    // First recur on left child
    printInorder(node->left);
 
    // Then print the data of node
    cout << node->data << " ";
 
    // Now recur on right child
    printInorder(node->right);
}
 
// Driver code
int main()
{
    struct Node* root = newNode(1);
    root->left = newNode(2);
    root->right = newNode(3);
    root->left->left = newNode(4);
    root->left->right = newNode(5);
 
    // Function call
    cout << "Inorder traversal of binary tree is \n";
    printInorder(root);
 
    return 0;
}


Java




// Java program for different tree traversals
 
// Class containing left and right child of current
// node and key value
class Node {
    int key;
    Node left, right;
 
    public Node(int item)
    {
        key = item;
        left = right = null;
    }
}
 
class BinaryTree {
 
    // Root of Binary Tree
    Node root;
 
    BinaryTree() { root = null; }
 
    // Given a binary tree, print its nodes in inorder
    void printInorder(Node node)
    {
        if (node == null)
            return;
 
        // First recur on left child
        printInorder(node.left);
 
        // Then print the data of node
        System.out.print(node.key + " ");
 
        // Now recur on right child
        printInorder(node.right);
    }
 
    // Driver code
    public static void main(String[] args)
    {
        BinaryTree tree = new BinaryTree();
        tree.root = new Node(1);
        tree.root.left = new Node(2);
        tree.root.right = new Node(3);
        tree.root.left.left = new Node(4);
        tree.root.left.right = new Node(5);
 
        // Function call
        System.out.println(
            "Inorder traversal of binary tree is ");
        tree.printInorder(tree.root);
    }
}


Python3




# Python3 program to for tree traversals
 
 
# A class that represents an individual node in a
# Binary Tree
class Node:
    def __init__(self, key):
        self.left = None
        self.right = None
        self.val = key
 
 
# A function to do inorder tree traversal
def printInorder(root):
 
    if root:
 
        # First recur on left child
        printInorder(root.left)
 
        # Then print the data of node
        print(root.val, end=" "),
 
        # Now recur on right child
        printInorder(root.right)
 
 
# Driver code
if __name__ == "__main__":
    root = Node(1)
    root.left = Node(2)
    root.right = Node(3)
    root.left.left = Node(4)
    root.left.right = Node(5)
 
    # Function call
    print("Inorder traversal of binary tree is")
    printInorder(root)


C#




// C# program for different
// tree traversals
using System;
 
// Class containing left and right child of
// current node and key value
class Node {
    public int key;
    public Node left, right;
 
    public Node(int item)
    {
        key = item;
        left = right = null;
    }
}
 
class BinaryTree {
 
    // Root of Binary Tree
    Node root;
 
    BinaryTree() { root = null; }
 
    // Given a binary tree, print
    // its nodes in inorder
    void printInorder(Node node)
    {
        if (node == null)
            return;
 
        // First recur on left child
        printInorder(node.left);
 
        // Then print the data of node
        Console.Write(node.key + " ");
 
        // Now recur on right child
        printInorder(node.right);
    }
 
    // Wrappers over above recursive functions
    void printInorder() { printInorder(root); }
 
    // Driver Code
    static public void Main(String[] args)
    {
        BinaryTree tree = new BinaryTree();
        tree.root = new Node(1);
        tree.root.left = new Node(2);
        tree.root.right = new Node(3);
        tree.root.left.left = new Node(4);
        tree.root.left.right = new Node(5);
 
        // Function call
        Console.WriteLine("Inorder traversal "
                          + "of binary tree is ");
        tree.printInorder();
    }
}
 
// This code is contributed by Arnab Kundu


Javascript




// javascript program for different tree traversals
 
// Class containing left and right child of current
// node and key value
class Node {
    constructor(val) {
        this.key = val;
        this.left = null;
        this.right = null;
    }
}
 
// Root of Binary Tree
var root = null;
     
// Given a binary tree, print its nodes in inorder
function printInorder(node) {
    if (node == null)
        return;
 
    // First recur on left child */
    printInorder(node.left);
 
    // Then print the data of node
    console.log(node.key + " ");
 
    // Now recur on right child
    printInorder(node.right);
}
 
// Driver method
     
    root = new Node(1);
    root.left = new Node(2);
    root.right = new Node(3);
    root.left.left = new Node(4);
    root.left.right = new Node(5);
 
    console.log("Inorder traversal of binary tree is ");
    printInorder(root);
 
// This code is contributed by aashish1995


Output

Inorder traversal of binary tree is 
4 2 5 1 3 

Time Complexity: O(N)
Auxiliary Space: If we don’t consider the size of the stack for function calls then O(1) otherwise O(h) where h is the height of the tree. 

Preorder Traversal

Algorithm Preorder(tree)

  1. Visit the root.
  2. Traverse the left subtree, i.e., call Preorder(left->subtree)
  3. Traverse the right subtree, i.e., call Preorder(right->subtree) 

Uses of Preorder:

Preorder traversal is used to create a copy of the tree. Preorder traversal is also used to get prefix expressions on an expression tree.

Code implementation of Preorder traversal:

C




// C program for different tree traversals
#include <stdio.h>
#include <stdlib.h>
 
// A binary tree node has data, pointer to left child
// and a pointer to right child
struct node {
    int data;
    struct node* left;
    struct node* right;
};
 
// Helper function that allocates a new node with the
// given data and NULL left and right pointers.
struct node* newNode(int data)
{
    struct node* node
        = (struct node*)malloc(sizeof(struct node));
    node->data = data;
    node->left = NULL;
    node->right = NULL;
 
    return (node);
}
 
// Given a binary tree, print its nodes in preorder
void printPreorder(struct node* node)
{
    if (node == NULL)
        return;
 
    // First print data of node
    printf("%d ", node->data);
 
    // Then recur on left subtree
    printPreorder(node->left);
 
    // Now recur on right subtree
    printPreorder(node->right);
}
 
// Driver code
int main()
{
    struct node* root = newNode(1);
    root->left = newNode(2);
    root->right = newNode(3);
    root->left->left = newNode(4);
    root->left->right = newNode(5);
 
    // Function call
    printf("Preorder traversal of binary tree is \n");
    printPreorder(root);
 
    getchar();
    return 0;
}


C++




// C++ program for different tree traversals
#include <bits/stdc++.h>
using namespace std;
 
// A binary tree node has data, pointer to left child
// and a pointer to right child
struct Node {
    int data;
    struct Node *left, *right;
};
 
// Utility function to create a new tree node
Node* newNode(int data)
{
    Node* temp = new Node;
    temp->data = data;
    temp->left = temp->right = NULL;
    return temp;
}
 
// Given a binary tree, print its nodes in preorder
void printPreorder(struct Node* node)
{
    if (node == NULL)
        return;
 
    // First print data of node
    cout << node->data << " ";
 
    // Then recur on left subtree
    printPreorder(node->left);
 
    // Now recur on right subtree
    printPreorder(node->right);
}
 
// Driver code
int main()
{
    struct Node* root = newNode(1);
    root->left = newNode(2);
    root->right = newNode(3);
    root->left->left = newNode(4);
    root->left->right = newNode(5);
 
    // Function call
    cout << "Preorder traversal of binary tree is \n";
    printPreorder(root);
 
    return 0;
}


Java




// Java program for different tree traversals
 
// Class containing left and right child of current
// node and key value
class Node {
    int key;
    Node left, right;
 
    public Node(int item)
    {
        key = item;
        left = right = null;
    }
}
 
class BinaryTree {
 
    // Root of Binary Tree
    Node root;
 
    BinaryTree() { root = null; }
 
    // Given a binary tree, print its nodes in preorder
    void printPreorder(Node node)
    {
        if (node == null)
            return;
 
        // First print data of node
        System.out.print(node.key + " ");
 
        // Then recur on left subtree
        printPreorder(node.left);
 
        // Now recur on right subtree
        printPreorder(node.right);
    }
 
    // Driver code
    public static void main(String[] args)
    {
        BinaryTree tree = new BinaryTree();
        tree.root = new Node(1);
        tree.root.left = new Node(2);
        tree.root.right = new Node(3);
        tree.root.left.left = new Node(4);
        tree.root.left.right = new Node(5);
 
        // Function call
        System.out.println(
            "Preorder traversal of binary tree is ");
        tree.printPreorder(tree.root);
    }
}


Python3




# Python3 program to for tree traversals
 
 
# A class that represents an individual node
# in a Binary Tree
class Node:
    def __init__(self, key):
        self.left = None
        self.right = None
        self.val = key
 
 
# A function to do preorder tree traversal
def printPreorder(root):
 
    if root:
 
        # First print the data of node
        print(root.val, end=" "),
 
        # Then recur on left child
        printPreorder(root.left)
 
        # Finally recur on right child
        printPreorder(root.right)
 
 
# Driver code
if __name__ == "__main__":
    root = Node(1)
    root.left = Node(2)
    root.right = Node(3)
    root.left.left = Node(4)
    root.left.right = Node(5)
 
    # Function call
    print("Preorder traversal of binary tree is")
    printPreorder(root)


C#




// C# program for different
// tree traversals
using System;
 
// Class containing left and right child of
// current node and key value
class Node {
    public int key;
    public Node left, right;
 
    public Node(int item)
    {
        key = item;
        left = right = null;
    }
}
 
class BinaryTree {
 
    // Root of Binary Tree
    Node root;
 
    BinaryTree() { root = null; }
 
    // Given a binary tree, print
    // its nodes in preorder
    void printPreorder(Node node)
    {
        if (node == null)
            return;
 
        // First print data of node
        Console.Write(node.key + " ");
 
        // Then recur on left subtree
        printPreorder(node.left);
 
        // Now recur on right subtree
        printPreorder(node.right);
    }
 
    // Driver Code
    static public void Main(String[] args)
    {
        BinaryTree tree = new BinaryTree();
        tree.root = new Node(1);
        tree.root.left = new Node(2);
        tree.root.right = new Node(3);
        tree.root.left.left = new Node(4);
        tree.root.left.right = new Node(5);
 
        // Function call
        Console.WriteLine("Preorder traversal "
                          + "of binary tree is ");
        tree.printPreorder(tree.root);
    }
}
 
// This code is contributed by Arnab Kundu


Javascript




// javascript program for different tree traversals
 
// Class containing left and right child of current
// node and key value
class Node {
    constructor(val) {
        this.key = val;
        this.left = null;
        this.right = null;
    }
}
 
// Root of Binary Tree
var root = null;
 
// Given a binary tree, print its nodes in preorder
function printPreorder(node) {
    if (node == null)
        return;
 
    // First print data of node
    document.write(node.key + " ");
 
    // Then recur on left subtree
    printPreorder(node.left);
 
    // Now recur on right subtree
    printPreorder(node.right);
}
 
// Driver method  
     
    root = new Node(1);
    root.left = new Node(2);
    root.right = new Node(3);
    root.left.left = new Node(4);
    root.left.right = new Node(5);
 
    console.log("Preorder traversal of binary tree is ");
    printPreorder(root);
 
// This code is contributed by aashish1995


Output

Preorder traversal of binary tree is 
1 2 4 5 3 

Time Complexity: O(N)
Auxiliary Space: If we don’t consider the size of the stack for function calls then O(1) otherwise O(h) where h is the height of the tree. 

Postorder Traversal

Algorithm Postorder(tree)

  1. Traverse the left subtree, i.e., call Postorder(left->subtree)
  2. Traverse the right subtree, i.e., call Postorder(right->subtree)
  3. Visit the root

Uses of Postorder:

Postorder traversal is used to delete the tree. Please see the question for the deletion of a tree for details. Postorder traversal is also useful to get the postfix expression of an expression tree

Below is the implementation of the above traversal methods:

C




// C program for different tree traversals
#include <stdio.h>
#include <stdlib.h>
 
// A binary tree node has data, pointer to left child
// and a pointer to right child
struct node {
    int data;
    struct node* left;
    struct node* right;
};
 
// Helper function that allocates a new node with the
// given data and NULL left and right pointers.
struct node* newNode(int data)
{
    struct node* node
        = (struct node*)malloc(sizeof(struct node));
    node->data = data;
    node->left = NULL;
    node->right = NULL;
 
    return (node);
}
 
// Given a binary tree, print its nodes according to the
// "bottom-up" postorder traversal.
void printPostorder(struct node* node)
{
    if (node == NULL)
        return;
 
    // First recur on left subtree
    printPostorder(node->left);
 
    // Then recur on right subtree
    printPostorder(node->right);
 
    // Now deal with the node
    printf("%d ", node->data);
}
 
// Driver code
int main()
{
    struct node* root = newNode(1);
    root->left = newNode(2);
    root->right = newNode(3);
    root->left->left = newNode(4);
    root->left->right = newNode(5);
 
    // Function call
    printf("Postorder traversal of binary tree is \n");
    printPostorder(root);
 
    getchar();
    return 0;
}


C++




// C++ program for different tree traversals
#include <bits/stdc++.h>
using namespace std;
 
// A binary tree node has data, pointer to left child
// and a pointer to right child
struct Node {
    int data;
    struct Node *left, *right;
};
 
// Utility function to create a new tree node
Node* newNode(int data)
{
    Node* temp = new Node;
    temp->data = data;
    temp->left = temp->right = NULL;
    return temp;
}
 
// Given a binary tree, print its nodes according to the
// "bottom-up" postorder traversal.
void printPostorder(struct Node* node)
{
    if (node == NULL)
        return;
 
    // First recur on left subtree
    printPostorder(node->left);
 
    // Then recur on right subtree
    printPostorder(node->right);
 
    // Now deal with the node
    cout << node->data << " ";
}
 
// Driver code
int main()
{
    struct Node* root = newNode(1);
    root->left = newNode(2);
    root->right = newNode(3);
    root->left->left = newNode(4);
    root->left->right = newNode(5);
 
    // Function call
    cout << "Postorder traversal of binary tree is \n";
    printPostorder(root);
 
    return 0;
}


Java




// Java program for different tree traversals
 
// Class containing left and right child of current
// node and key value
class Node {
    int key;
    Node left, right;
 
    public Node(int item)
    {
        key = item;
        left = right = null;
    }
}
 
class BinaryTree {
 
    // Root of Binary Tree
    Node root;
 
    BinaryTree() { root = null; }
 
    // Given a binary tree, print its nodes according to the
    // "bottom-up" postorder traversal.
    void printPostorder(Node node)
    {
        if (node == null)
            return;
 
        // First recur on left subtree
        printPostorder(node.left);
 
        // Then recur on right subtree
        printPostorder(node.right);
 
        // Now deal with the node
        System.out.print(node.key + " ");
    }
 
    // Driver code
    public static void main(String[] args)
    {
        BinaryTree tree = new BinaryTree();
        tree.root = new Node(1);
        tree.root.left = new Node(2);
        tree.root.right = new Node(3);
        tree.root.left.left = new Node(4);
        tree.root.left.right = new Node(5);
 
        // Function call
        System.out.println(
            "Postorder traversal of binary tree is ");
        tree.printPostorder(tree.root);
    }
}


Python3




# Python3 program to for tree traversals
 
 
# A class that represents an individual node
# in a Binary Tree
class Node:
    def __init__(self, key):
        self.left = None
        self.right = None
        self.val = key
 
 
# A function to do postorder tree traversal
def printPostorder(root):
 
    if root:
 
        # First recur on left child
        printPostorder(root.left)
 
        # The recur on right child
        printPostorder(root.right)
 
        # Now print the data of node
        print(root.val, end=" "),
 
 
# Driver code
if __name__ == "__main__":
    root = Node(1)
    root.left = Node(2)
    root.right = Node(3)
    root.left.left = Node(4)
    root.left.right = Node(5)
 
    # Function call
    print("Postorder traversal of binary tree is")
    printPostorder(root)


C#




// C# program for different
// tree traversals
using System;
 
// Class containing left and right child
// of current node and key value
class Node {
    public int key;
    public Node left, right;
 
    public Node(int item)
    {
        key = item;
        left = right = null;
    }
}
 
class BinaryTree {
    // Root of Binary Tree
    Node root;
 
    BinaryTree() { root = null; }
 
    // Given a binary tree, print its nodes according to
    // the "bottom-up" postorder traversal.
    void printPostorder(Node node)
    {
        if (node == null)
            return;
 
        // First recur on left subtree
        printPostorder(node.left);
 
        // Then recur on right subtree
        printPostorder(node.right);
 
        // Now deal with the node
        Console.Write(node.key + " ");
    }
 
    // Driver Code
    static public void Main(String[] args)
    {
        BinaryTree tree = new BinaryTree();
        tree.root = new Node(1);
        tree.root.left = new Node(2);
        tree.root.right = new Node(3);
        tree.root.left.left = new Node(4);
        tree.root.left.right = new Node(5);
 
        // Function call
        Console.WriteLine("Postorder traversal "
                          + "of binary tree is ");
        tree.printPostorder(tree.root);
    }
}
 
// This code is contributed by Arnab Kundu


Javascript




// javascript program for different tree traversals
 
// Class containing left and right child of current
// node and key value
class Node {
    constructor(val) {
        this.key = val;
        this.left = null;
        this.right = null;
    }
}
 
// Root of Binary Tree
var root = null;
     
// Given a binary tree, print its nodes according
// to the "bottom-up" postorder traversal
function printPostorder(node) {
    if (node == null)
        return;
 
    // First recur on left subtree
    printPostorder(node.left);
 
    // Then recur on right subtree
    printPostorder(node.right);
 
    // Now deal with the node
    console.log(node.key + " ");
}
 
// Driver method
     
    root = new Node(1);
    root.left = new Node(2);
    root.right = new Node(3);
    root.left.left = new Node(4);
    root.left.right = new Node(5);
 
    console.log("Postorder traversal of binary tree is ");
    printPostorder(root);
 
// This code is contributed by aashish1995


Output

Postorder traversal of binary tree is 
4 5 2 3 1 

Some other Tree Traversals Techniques:

Some of the other tree traversals are:

Level Order Treversal

For each node, first, the node is visited and then it’s child nodes are put in a FIFO queue. Then again the first node is popped out and then it’s child nodes are put in a FIFO queue and repeat until queue becomes empty.

Example:

Input:

Level Order Treversal:
1
2 3
4 5 

Boundary Traversal

The Boundary Traversal of a Tree includes:

  1. left boundary (nodes on left excluding leaf nodes)
  2. leaves (consist of only the leaf nodes)
  3. right boundary (nodes on right excluding leaf nodes)

Diagonal Traversal

In the Diagonal Traversal of a Tree, all the nodes in a single diagonal will be printed one by one.

Input

unnamed

Diagonal Traversal of binary tree: 

 8 10 14

 3 6 7 13

 1 4

Feeling lost in the world of random DSA topics, wasting time without progress? It’s time for a change! Join our DSA course, where we’ll guide you on an exciting journey to master DSA efficiently and on schedule.
Ready to dive in? Explore our Free Demo Content and join our DSA course, trusted by over 100,000 neveropen!

RELATED ARTICLES

Most Popular

Recent Comments