Boundary Traversal of binary tree

Last Updated : 7 Oct, 2025

Given the root of a binary tree, Find its boundary traversal in anti-clockwise order, starting from the root.

The boundary of a binary tree consists of the following parts:

  1. Left Boundary: The nodes on the left edge of the tree, excluding the leaf nodes.
  2. Leaf Nodes: All the leaf nodes from left to right.
  3. Right Boundary: The nodes on the right edge of the tree, excluding the leaf nodes, traversed in bottom-up order.

Note:

  • If the root does not have a left subtree or right subtree, then the root itself is considered part of the respective boundary.
  • Each node in the boundary should appear only once in the traversal.

Input :

1-


Output : [1, 2, 4, 8, 9, 6, 7, 3]
Explanation:

420046670


Input :

3-


Output : [1, 4, 3, 2]
Explanation:

420046671


Try It Yourself
redirect icon

[Approach - 1] Using Recursion - O(n) Time and O(h) Space

The boundary traversal of a binary tree is done in three steps. First, we traverse the left boundary, starting from the root’s left child and moving downward, excluding any leaf nodes. Next, we collect all the leaf nodes of the tree from left to right using recursion. Finally, we traverse the right boundary, starting from the root’s right child and moving downward, again excluding leaf nodes, but the collected nodes are added in reverse order. By combining the left boundary, leaf nodes, and right boundary, we obtain the complete anti-clockwise boundary traversal of the tree.

C++
#include <iostream>
#include <vector>
using namespace std;

// Node Structure
class Node {
  public:
    int data;
    Node *left;
    Node *right;

    Node(int x) {
        data = x;
        left = right = nullptr;
    }
};

bool isLeaf(Node *node) {
    return node->left == nullptr && node->right == nullptr;
}

// Function to collect left boundary nodes
// (top-down order)
void collectLeft(Node* root, vector<int>& res) {
    
  	// exclude leaf node
    if (root == nullptr || isLeaf(root))
        return;
	
  	res.push_back(root->data);
    if (root->left) 
        collectLeft(root->left, res);
    
    else if (root->right)
        collectLeft(root->right, res);
}

// Function to collect all leaf nodes 
void collectLeaves(Node *root, vector<int> &res) {
    if (root == nullptr)
        return;
	
  	// Add leaf nodes
    if (isLeaf(root)) {
        res.push_back(root->data);
        return;
    }

    collectLeaves(root->left, res);
    collectLeaves(root->right, res);
}


// Function to collect right boundary nodes
// (bottom-up order)
void collectRight(Node* root, vector<int>& res) {
  	
  	// exclude leaf nodes
    if (root == nullptr || isLeaf(root)) 
        return;

    if (root->right)
        collectRight(root->right, res);

    else if (root->left) 
        collectRight(root->left, res);
	
	res.push_back(root->data);  
}

// Function to find Boundary Traversal of Binary Tree
vector<int> boundaryTraversal(Node *root) {
	vector<int> res;

    if (!root)
        return res;

    // Add root data if it's not a leaf
    if (!isLeaf(root))
        res.push_back(root->data);

    // Collect left boundary
    collectLeft(root->left, res);

    // Collect leaf nodes
    collectLeaves(root, res);

    // Collect right boundary
    collectRight(root->right, res);

    return res;
}

int main() {

    // Input Binary tree
    //            1
    //         /     \
    //       2         3
    //     /   \     /   \
    //    4     5   6     7
    //         / \
    //        8   9
    
    Node *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);
    
    root->right->left = new Node(6);
    root->right->right = new Node(7);
    
    root->left->right->left = new Node(8);
    root->left->right->right = new Node(9);


    vector<int> boundary = boundaryTraversal(root);

    for (int x : boundary)
        cout << x << " ";

    return 0;
}
Java
import java.util.ArrayList;
import java.util.List;

// Node Structure
class Node {
    int data;
    Node left, right;

    Node(int x) {
        data = x;
        left = right = null;
    }
}

class GFG {
    
    static boolean isLeaf(Node node) {
        return node.left == null && node.right == null;
    }

    // Function to collect left boundary nodes
    // (top-down order)
    static void collectLeft(Node root, ArrayList<Integer> res) {
        
        // exclude leaf node
        if (root == null || isLeaf(root))
            return;
        
        res.add(root.data);
        if (root.left != null) 
            collectLeft(root.left, res);
        
        else if (root.right != null)
            collectLeft(root.right, res);
    }

    // Function to collect all leaf nodes 
    static void collectLeaves(Node root, ArrayList<Integer> res) {
        if (root == null)
            return;
        
        // Add leaf nodes
        if (isLeaf(root)) {
            res.add(root.data);
            return;
        }

        collectLeaves(root.left, res);
        collectLeaves(root.right, res);
    }

    // Function to collect right boundary nodes
    // (bottom-up order)
    static void collectRight(Node root, ArrayList<Integer> res) {
        
        // exclude leaf nodes
        if (root == null || isLeaf(root)) 
            return;

        if (root.right != null)
            collectRight(root.right, res);

        else if (root.left != null) 
            collectRight(root.left, res);
        
        res.add(root.data);  
    }

    // Function to find Boundary Traversal of Binary Tree
    static ArrayList<Integer> boundaryTraversal(Node root) {
        ArrayList<Integer> res = new ArrayList<>();

        if (root == null)
            return res;

        // Add root data if it's not a leaf
        if (!isLeaf(root))
            res.add(root.data);

        // Collect left boundary
        collectLeft(root.left, res);

        // Collect leaf nodes
        collectLeaves(root, res);

        // Collect right boundary
        collectRight(root.right, res);

        return res;
    }

    public static void main(String[] args) {

        // Input Binary tree
        //            1
        //         /     \
        //       2         3
        //     /   \     /   \
        //    4     5   6     7
        //         / \
        //        8   9
        
        Node 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);
        
        root.right.left = new Node(6);
        root.right.right = new Node(7);
        
        root.left.right.left = new Node(8);
        root.left.right.right = new Node(9);

        List<Integer> boundary = boundaryTraversal(root);

        for (int x : boundary)
            System.out.print(x + " ");
    }
}
Python
# Node Structure
class Node:
    def __init__(self, x):
        self.data = x
        self.left = None
        self.right = None

def isLeaf(node):
    return node.left is None and node.right is None

# Function to collect left boundary nodes
# (top-down order)
def collectLeft(root, res):
    
    # exclude leaf node
    if root is None or isLeaf(root):
        return
    
    res.append(root.data)
    if root.left:
        collectLeft(root.left, res)
    
    elif root.right:
        collectLeft(root.right, res)

# Function to collect all leaf nodes 
def collectLeaves(root, res):
    if root is None:
        return
    
    # Add leaf nodes
    if isLeaf(root):
        res.append(root.data)
        return

    collectLeaves(root.left, res)
    collectLeaves(root.right, res)

# Function to collect right boundary nodes
# (bottom-up order)
def collectRight(root, res):
   
    # exclude leaf nodes
    if root is None or isLeaf(root):
        return

    if root.right:
        collectRight(root.right, res)
    
    elif root.left:
        collectRight(root.left, res)
    
    res.append(root.data)

# Function to find Boundary Traversal of Binary Tree
def boundaryTraversal(root):
    res = []

    if not root:
        return res

    # Add root data if it's not a leaf
    if not isLeaf(root):
        res.append(root.data)

    # Collect left boundary
    collectLeft(root.left, res)

    # Collect leaf nodes
    collectLeaves(root, res)

    # Collect right boundary
    collectRight(root.right, res)

    return res

if __name__ == "__main__":

    # Input Binary tree
    #            1
    #         /     \
    #       2         3
    #     /   \     /   \
    #    4     5   6     7
    #         / \
    #        8   9
    
    root = Node(1)
    root.left = Node(2)
    root.right = Node(3)
    
    root.left.left = Node(4)
    root.left.right = Node(5)
    
    root.right.left = Node(6)
    root.right.right = Node(7)
    
    root.left.right.left = Node(8)
    root.left.right.right = Node(9)

    boundary = boundaryTraversal(root)

    for x in boundary:
        print(x, end=" ")
C#
using System;
using System.Collections.Generic;

// Node Structure
class Node {
    public int data;
    public Node left;
    public Node right;

    public Node(int x) {
        data = x;
        left = right = null;
    }
}

class GFG {
    
    static bool isLeaf(Node node) {
        return node.left == null && node.right == null;
    }

    // Function to collect left boundary nodes
    // (top-down order)
    static void collectLeft(Node root, List<int> res) {
      
        // exclude leaf node
        if (root == null || isLeaf(root))
            return;

        res.Add(root.data);
        if (root.left != null)
            collectLeft(root.left, res);
        else if (root.right != null)
            collectLeft(root.right, res);
    }

    // Function to collect all leaf nodes 
    static void collectLeaves(Node root, List<int> res) {
        if (root == null)
            return;

        // Add leaf nodes
        if (isLeaf(root)) {
            res.Add(root.data);
            return;
        }

        collectLeaves(root.left, res);
        collectLeaves(root.right, res);
    }

    // Function to collect right boundary nodes
    // (bottom-up order)
    static void collectRight(Node root, List<int> res) {
        
        // exclude leaf nodes
        if (root == null || isLeaf(root))
            return;

        if (root.right != null)
            collectRight(root.right, res);
        else if (root.left != null)
            collectRight(root.left, res);

        res.Add(root.data);
    }

    // Function to find Boundary Traversal of Binary Tree
    static List<int> boundaryTraversal(Node root) {
        List<int> res = new List<int>();

        if (root == null)
            return res;

        // Add root data if it's not a leaf
        if (!isLeaf(root))
            res.Add(root.data);

        // Collect left boundary
        collectLeft(root.left, res);

        // Collect leaf nodes
        collectLeaves(root, res);

        // Collect right boundary
        collectRight(root.right, res);

        return res;
    }

    static void Main(string[] args)
    {
        // Input Binary tree
        //            1
        //         /     \
        //       2         3
        //     /   \     /   \
        //    4     5   6     7
        //         / \
        //        8   9

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

        root.right.left = new Node(6);
        root.right.right = new Node(7);

        root.left.right.left = new Node(8);
        root.left.right.right = new Node(9);

        List<int> boundary = boundaryTraversal(root);

        foreach (int x in boundary)
            Console.Write(x + " ");
    }
}
JavaScript
// Node Structure
class Node {
    constructor(x) {
        this.data = x;
        this.left = null;
        this.right = null;
    }
}

function isLeaf(node) {
    return node.left === null && node.right === null;
}

// Function to collect left boundary nodes
// (top-down order)
function collectLeft(root, res) {
    
    // exclude leaf node
    if (root === null || isLeaf(root))
        return;

    res.push(root.data);
    if (root.left !== null)
        collectLeft(root.left, res);
    else if (root.right !== null)
        collectLeft(root.right, res);
}

// Function to collect all leaf nodes
function collectLeaves(root, res) {
    if (root === null)
        return;

    // Add leaf nodes
    if (isLeaf(root)) {
        res.push(root.data);
        return;
    }

    collectLeaves(root.left, res);
    collectLeaves(root.right, res);
}

// Function to collect right boundary nodes
// (bottom-up order)
function collectRight(root, res) {
    
    // exclude leaf nodes
    if (root === null || isLeaf(root))
        return;

    if (root.right !== null)
        collectRight(root.right, res);
    else if (root.left !== null)
        collectRight(root.left, res);

    res.push(root.data);
}

// Function to find Boundary Traversal of Binary Tree
function boundaryTraversal(root) {
    let res = [];

    if (root === null)
        return res;

    // Add root data if it's not a leaf
    if (!isLeaf(root))
        res.push(root.data);

    // Collect left boundary
    collectLeft(root.left, res);

    // Collect leaf nodes
    collectLeaves(root, res);

    // Collect right boundary
    collectRight(root.right, res);

    return res;
}

// Driver Code
// Input Binary tree
//            1
//         /     \
//       2         3
//     /   \     /   \
//    4     5   6     7
//         / \
//        8   9

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

root.right.left = new Node(6);
root.right.right = new Node(7);

root.left.right.left = new Node(8);
root.left.right.right = new Node(9);

let boundary = boundaryTraversal(root);
console.log(boundary.join(" "));

Output
1 2 4 8 9 6 7 3 

[Approach - 2] Using Iteration and Morris Traversal - O(n) Time and O(h) Space

The idea is to reduce the auxiliary space used by the memory stack in the above approach. This approach is similar to the previous one, but instead of recursion, we use iteration to find the left and right boundaries, and use Morris Traversal to find the leaf nodes.

C++
#include <iostream>
#include <vector>
using namespace std;

// Node Structure
class Node {
  public:
    int data;
    Node *left;
    Node *right;

    Node(int x) {
        data = x;
        left = right = nullptr;
    }
};

bool isLeaf(Node *node) {
    return node->left == nullptr && node->right == nullptr;
}

// Function to collect the left boundary nodes
void collectLeft(Node *root, vector<int> &res) {
    if (root == nullptr)
        return;

    Node *curr = root;
    while (!isLeaf(curr)) {
        res.push_back(curr->data);

        if (curr->left)
            curr = curr->left;
        else
            curr = curr->right;
    }
}

// Function to collect the leaf nodes using Morris Traversal
void collectLeaves(Node* root, vector<int>& res) {
    Node* current = root;

    while (current) {
        if (current->left == nullptr) {
          
            // If it's a leaf node
            if (current->right == nullptr) 
                res.push_back(current->data);
            
            current = current->right;
        } 
      	else {
          
            // Find the inorder predecessor
            Node* predecessor = current->left;
            while (predecessor->right && predecessor->right != current) {
                predecessor = predecessor->right;
            }

            if (predecessor->right == nullptr) {
                predecessor->right = current;
                current = current->left;
            } 
          	else {
          	    
              	// If it's predecessor is a leaf node
                if (predecessor->left == nullptr) 
                    res.push_back(predecessor->data);
                
                predecessor->right = nullptr;
                current = current->right;
            }
        }
    }
}

// Function to collect the right boundary nodes
void collectRight(Node *root, vector<int> &res) {
    if (root == nullptr)
        return;

    Node *curr = root;
    vector<int> temp;
    while (!isLeaf(curr)) {
      
        temp.push_back(curr->data);

        if (curr->right)
            curr = curr->right;
        else
            curr = curr->left;
    }
    for (int i = temp.size() - 1; i >= 0; --i)
        res.push_back(temp[i]);
}

// Function to perform boundary traversal
vector<int> boundaryTraversal(Node *root) {
    vector<int> res;

    if (!root)
        return res;

    // Add root data if it's not a leaf
    if (!isLeaf(root))
        res.push_back(root->data);

    // Collect left boundary
    collectLeft(root->left, res);

    // Collect leaf nodes
    collectLeaves(root, res);

    // Collect right boundary
    collectRight(root->right, res);

    return res;
}

int main() {

    // Hardcoded Binary tree
    //            1
    //         /     \
    //       2         3
    //     /   \     /   \
    //    4     5   6     7
    //         / \
    //        8   9
    
    Node *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);
    
    root->right->left = new Node(6);
    root->right->right = new Node(7);
    
    root->left->right->left = new Node(8);
    root->left->right->right = new Node(9);

    vector<int> boundary = boundaryTraversal(root);

    for (int x : boundary)
        cout << x << " ";

    return 0;
}
Java
import java.util.ArrayList;
import java.util.List;

// Node Structure
class Node {
    int data;
    Node left, right;

    Node(int x) {
        data = x;
        left = right = null;
    }
}

class GFG {

    static boolean isLeaf(Node node) {
        return node.left == null && node.right == null;
    }

    
    // Function to collect the left boundary nodes
    static void collectLeft(Node root, ArrayList<Integer> res) {
        if (root == null)
            return;

        Node curr = root;
        while (!isLeaf(curr)) {
            res.add(curr.data);

            if (curr.left != null)
                curr = curr.left;
            else
                curr = curr.right;
        }
    }

    // Function to collect the leaf nodes using Morris Traversal
    static void collectLeaves(Node root, ArrayList<Integer> res) {
        Node current = root;

        while (current != null) {
            if (current.left == null) {

                // If it's a leaf node
                if (current.right == null)
                    res.add(current.data);

                current = current.right;
            } else {

                // Find the inorder predecessor
                Node predecessor = current.left;
                while (predecessor.right != null && predecessor.right != current) {
                    predecessor = predecessor.right;
                }

                if (predecessor.right == null) {
                    predecessor.right = current;
                    current = current.left;
                } else {
                    // If its predecessor is a leaf node
                    if (predecessor.left == null)
                        res.add(predecessor.data);

                    predecessor.right = null;
                    current = current.right;
                }
            }
        }
    }

    // Function to collect the right boundary nodes
    static void collectRight(Node root, ArrayList<Integer> res) {
        if (root == null)
            return;

        Node curr = root;
        ArrayList<Integer> temp = new ArrayList<>();
        while (!isLeaf(curr)) {

            temp.add(curr.data);

            if (curr.right != null)
                curr = curr.right;
            else
                curr = curr.left;
        }
        for (int i = temp.size() - 1; i >= 0; --i)
            res.add(temp.get(i));
    }

    // Function to perform boundary traversal
    static ArrayList<Integer> boundaryTraversal(Node root) {
        ArrayList<Integer> res = new ArrayList<>();

        if (root == null)
            return res;

        // Add root data if it's not a leaf
        if (!isLeaf(root))
            res.add(root.data);

        // Collect left boundary
        collectLeft(root.left, res);

        // Collect leaf nodes
        collectLeaves(root, res);

        // Collect right boundary
        collectRight(root.right, res);

        return res;
    }

    public static void main(String[] args) {

        // Hardcoded Binary tree
        //            1
        //         /     \
        //       2         3
        //     /   \     /   \
        //    4     5   6     7
        //         / \
        //        8   9

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

        root.right.left = new Node(6);
        root.right.right = new Node(7);

        root.left.right.left = new Node(8);
        root.left.right.right = new Node(9);

        ArrayList<Integer> boundary = boundaryTraversal(root);

        for (int x : boundary)
            System.out.print(x + " ");
    }
}
Python
# Node Structure
class Node:
    def __init__(self, x):
        self.data = x
        self.left = None
        self.right = None

def isLeaf(node):
    return node.left is None and node.right is None

# Function to collect the left boundary nodes
def collectLeft(root, res):
    if root is None:
        return

    curr = root
    while not isLeaf(curr):
        res.append(curr.data)

        if curr.left is not None:
            curr = curr.left
        else:
            curr = curr.right

# Function to collect the leaf nodes using Morris Traversal
def collectLeaves(root, res):
    current = root

    while current:
        if current.left is None:

            # If it's a leaf node
            if current.right is None:
                res.append(current.data)

            current = current.right
        else:

            # Find the inorder predecessor
            predecessor = current.left
            while predecessor.right and predecessor.right != current:
                predecessor = predecessor.right

            if predecessor.right is None:
                predecessor.right = current
                current = current.left
            else:
                # If its predecessor is a leaf node
                if predecessor.left is None:
                    res.append(predecessor.data)

                predecessor.right = None
                current = current.right

# Function to collect the right boundary nodes
def collectRight(root, res):
    if root is None:
        return

    curr = root
    temp = []
    while not isLeaf(curr):
        temp.append(curr.data)

        if curr.right is not None:
            curr = curr.right
        else:
            curr = curr.left

    for i in reversed(temp):
        res.append(i)

# Function to perform boundary traversal
def boundaryTraversal(root):
    res = []

    if root is None:
        return res

    # Add root data if it's not a leaf
    if not isLeaf(root):
        res.append(root.data)

    # Collect left boundary
    collectLeft(root.left, res)

    # Collect leaf nodes
    collectLeaves(root, res)

    # Collect right boundary
    collectRight(root.right, res)

    return res

if __name__ == "__main__":

    # Hardcoded Binary tree
    #            1
    #         /     \
    #       2         3
    #     /   \     /   \
    #    4     5   6     7
    #         / \
    #        8   9

    root = Node(1)
    root.left = Node(2)
    root.right = Node(3)

    root.left.left = Node(4)
    root.left.right = Node(5)

    root.right.left = Node(6)
    root.right.right = Node(7)

    root.left.right.left = Node(8)
    root.left.right.right = Node(9)

    boundary = boundaryTraversal(root)
    print(" ".join(map(str, boundary)))
C#
using System;
using System.Collections.Generic;

// Node Structure
class Node {
    public int data;
    public Node left;
    public Node right;

    public Node(int x)
    {
        data = x;
        left = right = null;
    }
}

class GFG {
    static bool isLeaf(Node node) {
        return node.left == null && node.right == null;
    }

    // Function to collect the left boundary nodes
    static void collectLeft(Node root, List<int> res) {
        if (root == null)
            return;

        Node curr = root;
        while (!isLeaf(curr))
        {
            res.Add(curr.data);

            if (curr.left != null)
                curr = curr.left;
            else
                curr = curr.right;
        }
    }

    // Function to collect the leaf nodes using Morris Traversal
    static void collectLeaves(Node root, List<int> res)
    {
        Node current = root;

        while (current != null)
        {
            if (current.left == null)
            {
                // If it's a leaf node
                if (current.right == null)
                    res.Add(current.data);

                current = current.right;
            }
            else
            {
                // Find the inorder predecessor
                Node predecessor = current.left;
                while (predecessor.right != null && predecessor.right != current)
                {
                    predecessor = predecessor.right;
                }

                if (predecessor.right == null)
                {
                    predecessor.right = current;
                    current = current.left;
                }
                else
                {
                    // If its predecessor is a leaf node
                    if (predecessor.left == null)
                        res.Add(predecessor.data);

                    predecessor.right = null;
                    current = current.right;
                }
            }
        }
    }

    // Function to collect the right boundary nodes
    static void collectRight(Node root, List<int> res)
    {
        if (root == null)
            return;

        Node curr = root;
        List<int> temp = new List<int>();
        while (!isLeaf(curr))
        {
            temp.Add(curr.data);

            if (curr.right != null)
                curr = curr.right;
            else
                curr = curr.left;
        }

        for (int i = temp.Count - 1; i >= 0; --i)
            res.Add(temp[i]);
    }

    // Function to perform boundary traversal
    static List<int> boundaryTraversal(Node root)
    {
        List<int> res = new List<int>();

        if (root == null)
            return res;

        // Add root data if it's not a leaf
        if (!isLeaf(root))
            res.Add(root.data);

        // Collect left boundary
        collectLeft(root.left, res);

        // Collect leaf nodes
        collectLeaves(root, res);

        // Collect right boundary
        collectRight(root.right, res);

        return res;
    }

    static void Main(string[] args)
    {
        // Hardcoded Binary tree
        //            1
        //         /     \
        //       2         3
        //     /   \     /   \
        //    4     5   6     7
        //         / \
        //        8   9

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

        root.right.left = new Node(6);
        root.right.right = new Node(7);

        root.left.right.left = new Node(8);
        root.left.right.right = new Node(9);

        List<int> boundary = boundaryTraversal(root);

        foreach (int x in boundary)
            Console.Write(x + " ");
    }
}
JavaScript
// Node Structure
class Node {
    constructor(x) {
        this.data = x;
        this.left = null;
        this.right = null;
    }
}

function isLeaf(node) {
    return node.left === null && node.right === null;
}

// Function to collect the left boundary nodes
function collectLeft(root, res) {
    if (root === null)
        return;

    let curr = root;
    while (!isLeaf(curr)) {
        res.push(curr.data);

        if (curr.left !== null)
            curr = curr.left;
        else
            curr = curr.right;
    }
}

// Function to collect the leaf nodes using Morris Traversal
function collectLeaves(root, res) {
    let current = root;

    while (current) {
        if (current.left === null) {
            // If it's a leaf node
            if (current.right === null)
                res.push(current.data);

            current = current.right;
        } else {
            // Find the inorder predecessor
            let predecessor = current.left;
            while (predecessor.right && predecessor.right !== current) {
                predecessor = predecessor.right;
            }

            if (predecessor.right === null) {
                predecessor.right = current;
                current = current.left;
            } else {
                // If its predecessor is a leaf node
                if (predecessor.left === null)
                    res.push(predecessor.data);

                predecessor.right = null;
                current = current.right;
            }
        }
    }
}

// Function to collect the right boundary nodes
function collectRight(root, res) {
    if (root === null)
        return;

    let curr = root;
    let temp = [];
    while (!isLeaf(curr)) {
        temp.push(curr.data);

        if (curr.right !== null)
            curr = curr.right;
        else
            curr = curr.left;
    }

    for (let i = temp.length - 1; i >= 0; i--)
        res.push(temp[i]);
}

// Function to perform boundary traversal
function boundaryTraversal(root) {
    let res = [];

    if (root === null)
        return res;

    // Add root data if it's not a leaf
    if (!isLeaf(root))
        res.push(root.data);

    // Collect left boundary
    collectLeft(root.left, res);

    // Collect leaf nodes
    collectLeaves(root, res);

    // Collect right boundary
    collectRight(root.right, res);

    return res;
}

// Driver Code

// Hardcoded Binary tree
//            1
//         /     \
//       2         3
//     /   \     /   \
//    4     5   6     7
//         / \
//        8   9

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

root.right.left = new Node(6);
root.right.right = new Node(7);

root.left.right.left = new Node(8);
root.left.right.right = new Node(9);

let boundary = boundaryTraversal(root);
console.log(boundary.join(" "));

Output
1 2 4 8 9 6 7 3 
Comment