Find Height of Binary Tree represented by Parent array

Last Updated : 13 Jul, 2026

Given a parent array arr[] representing a binary tree, where arr[i] denotes the parent of node i, return the height of the tree. The root is the unique node whose parent is -1.

Note: The height of a tree is the number of nodes on the longest path from the root to a leaf.

Examples:

Input: arr[] = [-1, 0, 0, 1, 1, 3, 5]
Output: 5
Explanation: The longest path from the root node 0 to a leaf is 0 -> 1 -> 3 -> 5 -> 6, which contains 5 nodes. Therefore, the height of the tree is 5.

011

Input: arr[] = [-1, 0, 0]
Output: 2
Explanation: The longest root-to-leaf path is either 0 -> 1 or 0 -> 2, each containing 2 nodes. Therefore, the height of the tree is 2.

012
Try It Yourself
redirect icon

[Naive Approach] Brute Force Approach - O(n^2) Time and O(1) Space

The idea is to determine the depth of every node by repeatedly moving to its parent until the root is reached. Since the height of a tree is the maximum depth among all its nodes, we compute the depth of each node and return the largest one.

  • Initialize a variable height to store the maximum depth of the tree.
  • Traverse each node in the parent array.
  • For every node, repeatedly move to its parent until the root (-1) is reached, counting the number of nodes visited as its depth.
  • Compare the current node's depth with height and update height if it is larger.
  • Repeat this process for all nodes in the array.
  • Return the maximum depth obtained as the height of the tree.
C++
#include <algorithm>
#include <iostream>
#include <vector>
using namespace std;

// Returns the height of the binary tree represented by the parent array.
int findHeight(vector<int> &arr)
{
    int n = arr.size();

    // Stores the maximum depth found so far.
    int height = 0;

    // Traverse every node in the tree.
    for (int i = 0; i < n; i++)
    {
        int depth = 0;
        int node = i;

        // Move upwards through the parent chain until the root is reached.
        while (node != -1)
        {
            depth++;
            node = arr[node];
        }

        // Update the maximum depth encountered.
        height = max(height, depth);
    }

    return height;
}

int main()
{
    // Parent array representation of the binary tree.
    // Index  : 0  1  2  3  4  5  6
    // Parent : -1 0  0  1  1  3  5
    vector<int> arr = {-1, 0, 0, 1, 1, 3, 5};

    cout << findHeight(arr) << endl;

    return 0;
}
Java
import java.util.*;

public class GFG {

    // Returns the height of the binary tree represented by
    // the parent array.
    static int findHeight(int[] arr)
    {
        int n = arr.length;

        // Stores the maximum depth found so far.
        int height = 0;

        // Traverse every node in the tree.
        for (int i = 0; i < n; i++) {
            int depth = 0;
            int node = i;

            // Move upwards through the parent chain until
            // the root is reached.
            while (node != -1) {
                depth++;
                node = arr[node];
            }

            // Update the maximum depth encountered.
            height = Math.max(height, depth);
        }

        return height;
    }

    public static void main(String[] args)
    {
        // Parent array representation of the binary tree.
        // Index  : 0  1  2  3  4  5  6
        // Parent : -1 0  0  1  1  3  5
        int[] arr = { -1, 0, 0, 1, 1, 3, 5 };

        System.out.println(findHeight(arr));
    }
}
Python
# Returns the height of the binary tree represented by the parent array.
def findHeight(arr):
    n = len(arr)

    # Stores the maximum depth found so far.
    height = 0

    # Traverse every node in the tree.
    for i in range(n):
        depth = 0
        node = i

        # Move upwards through the parent chain until the root is reached.
        while node != -1:
            depth += 1
            node = arr[node]

        # Update the maximum depth encountered.
        height = max(height, depth)

    return height

# Driver Code

if __name__ == "__main__":
    # Parent array representation of the binary tree.
    # Index  : 0  1  2  3  4  5  6
    # Parent : -1 0  0  1  1  3  5
    arr = [-1, 0, 0, 1, 1, 3, 5]

    print(findHeight(arr))
C#
using System;

class GFG {
    
    // Returns the height of the binary tree represented by
    // the parent array.
    static int findHeight(int[] arr)
    {
        int n = arr.Length;

        // Stores the maximum depth found so far.
        int height = 0;

        // Traverse every node in the tree.
        for (int i = 0; i < n; i++) {
            int depth = 0;
            int node = i;

            // Move upwards through the parent chain until
            // the root is reached.
            while (node != -1) {
                depth++;
                node = arr[node];
            }

            // Update the maximum depth encountered.
            height = Math.Max(height, depth);
        }

        return height;
    }

    static void Main()
    {
        // Parent array representation of the binary tree.
        // Index  : 0  1  2  3  4  5  6
        // Parent : -1 0  0  1  1  3  5
        int[] arr = { -1, 0, 0, 1, 1, 3, 5 };

        Console.WriteLine(findHeight(arr));
    }
}
JavaScript
// Returns the height of the binary tree represented by the
// parent array.
function findHeight(arr)
{
    const n = arr.length;

    // Stores the maximum depth found so far.
    let height = 0;

    // Traverse every node in the tree.
    for (let i = 0; i < n; i++) {
        let depth = 0;
        let node = i;

        // Move upwards through the parent chain until the
        // root is reached.
        while (node !== -1) {
            depth++;
            node = arr[node];
        }

        // Update the maximum depth encountered.
        height = Math.max(height, depth);
    }

    return height;
}

// Driver Code

// Parent array representation of the binary tree.
// Index  : 0  1  2  3  4  5  6
// Parent : -1 0  0  1  1  3  5
const arr = [ -1, 0, 0, 1, 1, 3, 5 ];
console.log(findHeight(arr));

Output
5

[Better Approach] By Constructing tree and Level Order Traversal - O(n) Time and O(n) Space

The idea is to reconstruct the binary tree using parent array because parent array stores parent-child relationships. Once the tree is built, we perform a level order traversal (BFS), where each level corresponds to one level of the tree, and the total number of levels gives its height.

  • Create a tree node for every index in the parent array.
  • Traverse the parent array and connect each node to its parent as either the left or right child, while identifying the root node.
  • Initialize a queue and insert the root into it.
  • Perform a level order traversal by processing all nodes at the current level before moving to the next.
  • After processing each level, increment the height by one.
  • Continue until the queue becomes empty and return the computed height.
C++
#include <iostream>
#include <queue>
#include <vector>
using namespace std;

class Node
{
  public:
    int val;
    Node *left, *right;

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

// Returns the height of the binary tree represented by the parent array.
int findHeight(vector<int> &arr)
{
    int n = arr.size();

    if (n == 0)
        return 0;

    // Create a tree node for every index.
    vector<Node *> nodes(n);
    for (int i = 0; i < n; i++)
        nodes[i] = new Node(i);

    Node *root = nullptr;

    // Build the binary tree from the parent array.
    for (int i = 0; i < n; i++)
    {
        if (arr[i] == -1)
        {
            root = nodes[i];
        }
        else
        {
            // Attach the node as the left child if vacant,
            // otherwise as the right child.
            if (nodes[arr[i]]->left == nullptr)
                nodes[arr[i]]->left = nodes[i];
            else
                nodes[arr[i]]->right = nodes[i];
        }
    }

    // Perform level order traversal to calculate the height.
    queue<Node *> q;
    q.push(root);

    int height = 0;

    while (!q.empty())
    {
        int size = q.size();

        while (size--)
        {
            Node *curr = q.front();
            q.pop();

            if (curr->left)
                q.push(curr->left);

            if (curr->right)
                q.push(curr->right);
        }

        // One complete level has been processed.
        height++;
    }

    return height;
}

int main()
{
    // Parent array representation of the binary tree.
    vector<int> arr = {-1, 0, 0, 1, 1, 3, 5};
    cout << findHeight(arr);

    return 0;
}
Java
import java.util.*;

class Node {
    int val;
    Node left, right;

    Node(int x) { val = x; }
}

public class GFG {

    // Returns the height of the binary tree represented by
    // the parent array.
    static int findHeight(int[] arr)
    {
        int n = arr.length;

        if (n == 0)
            return 0;

        // Create a tree node for every index.
        Node[] nodes = new Node[n];
        for (int i = 0; i < n; i++)
            nodes[i] = new Node(i);

        Node root = null;

        // Build the binary tree from the parent array.
        for (int i = 0; i < n; i++) {

            if (arr[i] == -1) {
                root = nodes[i];
            }
            else {

                // Attach the node as the left child if
                // vacant, otherwise as the right child.
                if (nodes[arr[i]].left == null)
                    nodes[arr[i]].left = nodes[i];
                else
                    nodes[arr[i]].right = nodes[i];
            }
        }

        // Perform level order traversal to calculate the
        // height.
        Queue<Node> q = new LinkedList<>();
        q.offer(root);

        int height = 0;

        while (!q.isEmpty()) {

            int size = q.size();

            while (size-- > 0) {

                Node curr = q.poll();

                if (curr.left != null)
                    q.offer(curr.left);

                if (curr.right != null)
                    q.offer(curr.right);
            }

            // One complete level has been processed.
            height++;
        }

        return height;
    }

    public static void main(String[] args)
    {
        // Parent array representation of the binary tree.
        int[] arr = { -1, 0, 0, 1, 1, 3, 5 };

        System.out.println(findHeight(arr));
    }
}
Python
from collections import deque

class Node:
    def __init__(self, x):
        self.val = x
        self.left = None
        self.right = None


# Returns the height of the binary tree represented by the parent array.
def findHeight(arr):

    n = len(arr)

    if n == 0:
        return 0

    # Create a tree node for every index.
    nodes = [Node(i) for i in range(n)]

    root = None

    # Build the binary tree from the parent array.
    for i in range(n):

        if arr[i] == -1:
            root = nodes[i]
        else:

            # Attach the node as the left child if vacant,
            # otherwise as the right child.
            if nodes[arr[i]].left is None:
                nodes[arr[i]].left = nodes[i]
            else:
                nodes[arr[i]].right = nodes[i]

    # Perform level order traversal to calculate the height.
    q = deque([root])

    height = 0

    while q:

        size = len(q)

        while size:

            curr = q.popleft()

            if curr.left:
                q.append(curr.left)

            if curr.right:
                q.append(curr.right)

            size -= 1

        # One complete level has been processed.
        height += 1

    return height

# Driver Code

if __name__ == "__main__":
    # Parent array representation of the binary tree.
    arr = [-1, 0, 0, 1, 1, 3, 5]

    print(findHeight(arr))
C#
using System;
using System.Collections.Generic;

class Node {
    public int val;
    public Node left, right;

    public Node(int x) { val = x; }
}

class GFG {
    // Returns the height of the binary tree represented by
    // the parent array.
    static int findHeight(int[] arr)
    {
        int n = arr.Length;

        if (n == 0)
            return 0;

        // Create a tree node for every index.
        Node[] nodes = new Node[n];
        for (int i = 0; i < n; i++)
            nodes[i] = new Node(i);

        Node root = null;

        // Build the binary tree from the parent array.
        for (int i = 0; i < n; i++) {
            if (arr[i] == -1) {
                root = nodes[i];
            }
            else {
                // Attach the node as the left child if
                // vacant, otherwise as the right child.
                if (nodes[arr[i]].left == null)
                    nodes[arr[i]].left = nodes[i];
                else
                    nodes[arr[i]].right = nodes[i];
            }
        }

        // Perform level order traversal to calculate the
        // height.
        Queue<Node> q = new Queue<Node>();
        q.Enqueue(root);

        int height = 0;

        while (q.Count > 0) {
            int size = q.Count;

            while (size-- > 0) {
                Node curr = q.Dequeue();

                if (curr.left != null)
                    q.Enqueue(curr.left);

                if (curr.right != null)
                    q.Enqueue(curr.right);
            }

            // One complete level has been processed.
            height++;
        }

        return height;
    }

    static void Main()
    {
        // Parent array representation of the binary tree.
        int[] arr = { -1, 0, 0, 1, 1, 3, 5 };

        Console.WriteLine(findHeight(arr));
    }
}
JavaScript
class Node {
    constructor(val)
    {
        this.val = val;
        this.left = null;
        this.right = null;
    }
}

// Returns the height of the binary tree represented by the
// parent array.
function findHeight(arr)
{
    const n = arr.length;

    if (n === 0)
        return 0;

    // Create a tree node for every index.
    const nodes = [];

    for (let i = 0; i < n; i++)
        nodes.push(new Node(i));

    let root = null;

    // Build the binary tree from the parent array.
    for (let i = 0; i < n; i++) {

        if (arr[i] === -1) {
            root = nodes[i];
        }
        else {

            // Attach the node as the left child if vacant,
            // otherwise as the right child.
            if (nodes[arr[i]].left === null)
                nodes[arr[i]].left = nodes[i];
            else
                nodes[arr[i]].right = nodes[i];
        }
    }

    // Perform level order traversal to calculate the
    // height.
    const q = [ root ];

    let height = 0;

    while (q.length > 0) {

        let size = q.length;

        while (size--) {

            const curr = q.shift();

            if (curr.left)
                q.push(curr.left);

            if (curr.right)
                q.push(curr.right);
        }

        // One complete level has been processed.
        height++;
    }

    return height;
}

// Driver Code

// Parent array representation of the binary tree.
const arr = [ -1, 0, 0, 1, 1, 3, 5 ];
console.log(findHeight(arr));

Output
5

[Expected Approach] Using Dynamic Programming - O(n) Time and O(n) Space

Instead of constructing the binary tree, we directly use the parent array to compute the depth of each node. While moving towards the root, if we encounter a node whose depth is already known, we reuse it and assign depths to all visited nodes, ensuring each node's depth is computed only once.

  • Create a height array initialized with 0 to store the depth of each node.
  • Traverse every node in the parent array.
  • From the current node, move towards the root until reaching either the root or a node whose depth has already been computed.
  • Use the known depth (if available) to determine the depth of the current node.
  • Traverse the same path again and assign depths to all previously unvisited nodes while moving upward.
  • Keep updating the maximum depth encountered and return it as the height of the tree.
C++
#include <algorithm>
#include <iostream>
#include <vector>
using namespace std;

// Returns the height of the binary tree represented by the parent array.
int findHeight(vector<int> &arr)
{
    int n = arr.size();

    // Stores the depth of each node.
    vector<int> height(n, 0);

    int res = 0;

    // Traverse every node.
    for (int i = 0; i < n; i++)
    {
        int node = i;
        int cnt = 0;

        // Move upwards until reaching the root
        // or a node whose depth is already known.
        while (node != -1 && height[node] == 0)
        {
            cnt++;
            node = arr[node];
        }

        // Reuse the already computed depth.
        if (node != -1)
            cnt += height[node];

        node = i;

        // Assign depths to all unvisited nodes on this path.
        while (node != -1 && height[node] == 0)
        {
            height[node] = cnt;
            cnt--;
            node = arr[node];
        }

        // Update the maximum depth.
        res = max(res, height[i]);
    }

    return res;
}

int main()
{
    // Parent array representation of the binary tree.
    vector<int> arr = {-1, 0, 0, 1, 1, 3, 5};
    cout << findHeight(arr);

    return 0;
}
Java
import java.util.*;

public class GFG {

    // Returns the height of the binary tree represented by
    // the parent array.
    static int findHeight(int[] arr)
    {
        int n = arr.length;

        // Stores the depth of each node.
        int[] height = new int[n];

        int res = 0;

        // Traverse every node.
        for (int i = 0; i < n; i++) {

            int node = i;
            int cnt = 0;

            // Move upwards until reaching the root
            // or a node whose depth is already known.
            while (node != -1 && height[node] == 0) {
                cnt++;
                node = arr[node];
            }

            // Reuse the already computed depth.
            if (node != -1)
                cnt += height[node];

            node = i;

            // Assign depths to all unvisited nodes on this
            // path.
            while (node != -1 && height[node] == 0) {
                height[node] = cnt;
                cnt--;
                node = arr[node];
            }

            // Update the maximum depth.
            res = Math.max(res, height[i]);
        }

        return res;
    }

    public static void main(String[] args)
    {
        // Parent array representation of the binary tree.
        int[] arr = { -1, 0, 0, 1, 1, 3, 5 };

        System.out.println(findHeight(arr));
    }
}
Python
# Returns the height of the binary tree represented by the parent array.
def findHeight(arr):

    n = len(arr)

    # Stores the depth of each node.
    height = [0] * n

    res = 0

    # Traverse every node.
    for i in range(n):

        node = i
        cnt = 0

        # Move upwards until reaching the root
        # or a node whose depth is already known.
        while node != -1 and height[node] == 0:
            cnt += 1
            node = arr[node]

        # Reuse the already computed depth.
        if node != -1:
            cnt += height[node]

        node = i

        # Assign depths to all unvisited nodes on this path.
        while node != -1 and height[node] == 0:
            height[node] = cnt
            cnt -= 1
            node = arr[node]

        # Update the maximum depth.
        res = max(res, height[i])

    return res

# Driver Code

if __name__ == "__main__":
    # Parent array representation of the binary tree.
    arr = [-1, 0, 0, 1, 1, 3, 5]

    print(findHeight(arr))
C#
using System;

class GFG {
    
    // Returns the height of the binary tree represented by
    // the parent array.
    static int findHeight(int[] arr)
    {
        int n = arr.Length;

        // Stores the depth of each node.
        int[] height = new int[n];

        int res = 0;

        // Traverse every node.
        for (int i = 0; i < n; i++) {
            int node = i;
            int cnt = 0;

            // Move upwards until reaching the root
            // or a node whose depth is already known.
            while (node != -1 && height[node] == 0) {
                cnt++;
                node = arr[node];
            }

            // Reuse the already computed depth.
            if (node != -1)
                cnt += height[node];

            node = i;

            // Assign depths to all unvisited nodes on this
            // path.
            while (node != -1 && height[node] == 0) {
                height[node] = cnt;
                cnt--;
                node = arr[node];
            }

            // Update the maximum depth.
            res = Math.Max(res, height[i]);
        }

        return res;
    }

    static void Main()
    {
        // Parent array representation of the binary tree.
        int[] arr = { -1, 0, 0, 1, 1, 3, 5 };
        Console.WriteLine(findHeight(arr));
    }
}
JavaScript
// Returns the height of the binary tree represented by the
// parent array.
function findHeight(arr)
{
    const n = arr.length;

    // Stores the depth of each node.
    const height = new Array(n).fill(0);

    let res = 0;

    // Traverse every node.
    for (let i = 0; i < n; i++) {

        let node = i;
        let cnt = 0;

        // Move upwards until reaching the root
        // or a node whose depth is already known.
        while (node !== -1 && height[node] === 0) {
            cnt++;
            node = arr[node];
        }

        // Reuse the already computed depth.
        if (node !== -1)
            cnt += height[node];

        node = i;

        // Assign depths to all unvisited nodes on this
        // path.
        while (node !== -1 && height[node] === 0) {
            height[node] = cnt;
            cnt--;
            node = arr[node];
        }

        // Update the maximum depth.
        res = Math.max(res, height[i]);
    }

    return res;
}

// Driver Code

// Parent array representation of the binary tree.
const arr = [ -1, 0, 0, 1, 1, 3, 5 ];
console.log(findHeight(arr));

Output
5
Comment