Construct Binary Tree from given Parent Array representation
Given an array that represents a tree in such a way that array indexes are values in tree nodes and array values give the parent node of that particular index (or node). The value of the root node index would always be -1 as there is no parent for root. Construct the standard linked representation of given Binary Tree from this given representation.
Examples:
Input: parent[] = {1, 5, 5, 2, 2, -1, 3} Output: root of below tree 5 / \ 1 2 / / \ 0 3 4 / 6 Explanation: Index of -1 is 5. So 5 is root. 5 is present at indexes 1 and 2. So 1 and 2 are children of 5. 1 is present at index 0, so 0 is child of 1. 2 is present at indexes 3 and 4. So 3 and 4 are children of 2. 3 is present at index 6, so 6 is child of 3. Input: parent[] = {-1, 0, 0, 1, 1, 3, 5}; Output: root of below tree 0 / \ 1 2 / \ 3 4 / 5 / 6
Expected time complexity is O(n) where n is number of elements in given array.
We strongly recommend to minimize your browser and try this yourself first.
A Simple Solution to recursively construct by first searching the current root, then recurring for the found indexes (there can be at most two indexes) and making them left and right subtrees of root. This solution takes O(n2) as we have to linearly search for every node.
An Efficient Solution can solve the above problem in O(n) time. The idea is to use extra space. An array created[0..n-1] is used to keep track of created nodes.
createTree(parent[], n)
- Create an array of pointers say created[0..n-1]. The value of created[i] is NULL if node for index i is not created, else value is pointer to the created node.
- Do following for every index i of given array
createNode(parent, i, created)
createNode(parent[], i, created[])
- If created[i] is not NULL, then node is already created. So return.
- Create a new node with value ‘i’.
- If parent[i] is -1 (i is root), make created node as root and return.
- Check if parent of ‘i’ is created (We can check this by checking if created[parent[i]] is NULL or not.
- If parent is not created, recur for parent and create the parent first.
- Let the pointer to parent be p. If p->left is NULL, then make the new node as left child. Else make the new node as right child of parent.
Following is C++ implementation of above idea.
C++14
// C++ program to construct a Binary Tree from parent array #include<bits/stdc++.h> using namespace std; // A tree node struct Node { int key; struct Node *left, *right; }; // Utility function to create new Node Node *newNode( int key) { Node *temp = new Node; temp->key = key; temp->left = temp->right = NULL; return (temp); } // Creates a node with key as 'i'. If i is root, then it changes // root. If parent of i is not created, then it creates parent first void createNode( int parent[], int i, Node *created[], Node **root) { // If this node is already created if (created[i] != NULL) return ; // Create a new node and set created[i] created[i] = newNode(i); // If 'i' is root, change root pointer and return if (parent[i] == -1) { *root = created[i]; return ; } // If parent is not created, then create parent first if (created[parent[i]] == NULL) createNode(parent, parent[i], created, root); // Find parent pointer Node *p = created[parent[i]]; // If this is first child of parent if (p->left == NULL) p->left = created[i]; else // If second child p->right = created[i]; } // Creates tree from parent[0..n-1] and returns root of the created tree Node *createTree( int parent[], int n) { // Create an array created[] to keep track // of created nodes, initialize all entries // as NULL Node *created[n]; for ( int i=0; i<n; i++) created[i] = NULL; Node *root = NULL; for ( int i=0; i<n; i++) createNode(parent, i, created, &root); return root; } //For adding new line in a program inline void newLine(){ cout << "\n" ; } // Utility function to do inorder traversal void inorder(Node *root) { if (root != NULL) { inorder(root->left); cout << root->key << " " ; inorder(root->right); } } // Driver method int main() { int parent[] = {-1, 0, 0, 1, 1, 3, 5}; int n = sizeof parent / sizeof parent[0]; Node *root = createTree(parent, n); cout << "Inorder Traversal of constructed tree\n" ; inorder(root); newLine(); } |
Java
// Java program to construct a binary tree from parent array // A binary tree node class Node { int key; Node left, right; public Node( int key) { this .key = key; left = right = null ; } } class BinaryTree { Node root; // Creates a node with key as 'i'. If i is root, then it changes // root. If parent of i is not created, then it creates parent first void createNode( int parent[], int i, Node created[]) { // If this node is already created if (created[i] != null ) return ; // Create a new node and set created[i] created[i] = new Node(i); // If 'i' is root, change root pointer and return if (parent[i] == - 1 ) { root = created[i]; return ; } // If parent is not created, then create parent first if (created[parent[i]] == null ) createNode(parent, parent[i], created); // Find parent pointer Node p = created[parent[i]]; // If this is first child of parent if (p.left == null ) p.left = created[i]; else // If second child p.right = created[i]; } /* Creates tree from parent[0..n-1] and returns root of the created tree */ Node createTree( int parent[], int n) { // Create an array created[] to keep track // of created nodes, initialize all entries // as NULL Node[] created = new Node[n]; for ( int i = 0 ; i < n; i++) created[i] = null ; for ( int i = 0 ; i < n; i++) createNode(parent, i, created); return root; } //For adding new line in a program void newLine() { System.out.println( "" ); } // Utility function to do inorder traversal void inorder(Node node) { if (node != null ) { inorder(node.left); System.out.print(node.key + " " ); inorder(node.right); } } // Driver method public static void main(String[] args) { BinaryTree tree = new BinaryTree(); int parent[] = new int []{- 1 , 0 , 0 , 1 , 1 , 3 , 5 }; int n = parent.length; Node node = tree.createTree(parent, n); System.out.println( "Inorder traversal of constructed tree " ); tree.inorder(node); tree.newLine(); } } // This code has been contributed by Mayank Jaiswal(mayank_24) |
Python3
# Python implementation to construct a Binary Tree from # parent array # A node structure class Node: # A utility function to create a new node def __init__( self , key): self .key = key self .left = None self .right = None """ Creates a node with key as 'i'. If i is root,then it changes root. If parent of i is not created, then it creates parent first """ def createNode(parent, i, created, root): # If this node is already created if created[i] is not None : return # Create a new node and set created[i] created[i] = Node(i) # If 'i' is root, change root pointer and return if parent[i] = = - 1 : root[ 0 ] = created[i] # root[0] denotes root of the tree return # If parent is not created, then create parent first if created[parent[i]] is None : createNode(parent, parent[i], created, root ) # Find parent pointer p = created[parent[i]] # If this is first child of parent if p.left is None : p.left = created[i] # If second child else : p.right = created[i] # Creates tree from parent[0..n-1] and returns root of the # created tree def createTree(parent): n = len (parent) # Create and array created[] to keep track # of created nodes, initialize all entries as None created = [ None for i in range (n + 1 )] root = [ None ] for i in range (n): createNode(parent, i, created, root) return root[ 0 ] #Inorder traversal of tree def inorder(root): if root is not None : inorder(root.left) print (root.key,end = " " ) inorder(root.right) # Driver Method parent = [ - 1 , 0 , 0 , 1 , 1 , 3 , 5 ] root = createTree(parent) print ( "Inorder Traversal of constructed tree" ) inorder(root) # This code is contributed by Nikhil Kumar Singh(nickzuck_007) |
C#
// C# program to construct a binary // tree from parent array using System; // A binary tree node public class Node { public int key; public Node left, right; public Node( int key) { this .key = key; left = right = null ; } } class GFG { public Node root; // Creates a node with key as 'i'. // If i is root, then it changes // root. If parent of i is not created, // then it creates parent first public virtual void createNode( int [] parent, int i, Node[] created) { // If this node is already created if (created[i] != null ) { return ; } // Create a new node and set created[i] created[i] = new Node(i); // If 'i' is root, change root // pointer and return if (parent[i] == -1) { root = created[i]; return ; } // If parent is not created, then // create parent first if (created[parent[i]] == null ) { createNode(parent, parent[i], created); } // Find parent pointer Node p = created[parent[i]]; // If this is first child of parent if (p.left == null ) { p.left = created[i]; } else // If second child { p.right = created[i]; } } /* Creates tree from parent[0..n-1] and returns root of the created tree */ public virtual Node createTree( int [] parent, int n) { // Create an array created[] to // keep track of created nodes, // initialize all entries as NULL Node[] created = new Node[n]; for ( int i = 0; i < n; i++) { created[i] = null ; } for ( int i = 0; i < n; i++) { createNode(parent, i, created); } return root; } // For adding new line in a program public virtual void newLine() { Console.WriteLine( "" ); } // Utility function to do inorder traversal public virtual void inorder(Node node) { if (node != null ) { inorder(node.left); Console.Write(node.key + " " ); inorder(node.right); } } // Driver Code public static void Main( string [] args) { GFG tree = new GFG(); int [] parent = new int []{-1, 0, 0, 1, 1, 3, 5}; int n = parent.Length; Node node = tree.createTree(parent, n); Console.WriteLine( "Inorder traversal of " + "constructed tree " ); tree.inorder(node); tree.newLine(); } } // This code is contributed by Shrikant13 |
Javascript
<script> // Javascript program to construct a binary // tree from parent array // A binary tree node class Node { constructor(key) { this .key = key; this .left = null ; this .right = null ; } } var root = null ; // Creates a node with key as 'i'. // If i is root, then it changes // root. If parent of i is not created, // then it creates parent first function createNode(parent, i, created) { // If this node is already created if (created[i] != null ) { return ; } // Create a new node and set created[i] created[i] = new Node(i); // If 'i' is root, change root // pointer and return if (parent[i] == -1) { root = created[i]; return ; } // If parent is not created, then // create parent first if (created[parent[i]] == null ) { createNode(parent, parent[i], created); } // Find parent pointer var p = created[parent[i]]; // If this is first child of parent if (p.left == null ) { p.left = created[i]; } else // If second child { p.right = created[i]; } } /* Creates tree from parent[0..n-1] and returns root of the created tree */ function createTree(parent, n) { // Create an array created[] to // keep track of created nodes, // initialize all entries as NULL var created = Array(n); for ( var i = 0; i < n; i++) { created[i] = null ; } for ( var i = 0; i < n; i++) { createNode(parent, i, created); } return root; } // For adding new line in a program function newLine() { document.write( "" ); } // Utility function to do inorder traversal function inorder(node) { if (node != null ) { inorder(node.left); document.write(node.key + " " ); inorder(node.right); } } // Driver Code var parent = [-1, 0, 0, 1, 1, 3, 5]; var n = parent.length; var node = createTree(parent, n); document.write( "Inorder traversal of " + "constructed tree<br>" ); inorder(node); newLine(); // This code is contributed by rrrtnx. </script> |
Inorder Traversal of constructed tree 6 5 3 1 4 0 2
Time Complexity: O(n^2)
In this approach, we iterate over the parent array, and in the worst case, we need to create a node for every element in the array. And in the createNode() function, the main time complexity is due to the recursive calls that depend on the height of the tree, which can be n. So, the overall time complexity of the algorithm is O(n^2).
Space Complexity: O(n)
The space complexity of the algorithm is linear, i.e., O(n), since we need to create a node for every element of the parent array.
Another Efficient Solution:
The idea is to first create all n new tree nodes, each having values from 0 to n – 1, where n is the size of parent array, and store them in any data structure like map, array etc to keep track of which node is created for which value. Then traverse the given parent array and build the tree by setting the parent-child relationship.
Following is the C++ implementation of the above idea.
C++
// C++ program to construct a Binary Tree from parent array #include <bits/stdc++.h> using namespace std; struct Node { int data; struct Node* left = NULL; struct Node* right = NULL; Node() {} Node( int x) { data = x; } }; // Function to construct binary tree from parent array. Node* createTree( int parent[], int n) { // Create an array to store the reference // of all newly created nodes corresponding // to node value vector<Node*> ref; // This root represent the root of the // newly constructed tree Node* root = new Node(); // Create n new tree nodes, each having // a value from 0 to n-1, and store them // in ref for ( int i = 0; i < n; i++) { Node* temp = new Node(i); ref.push_back(temp); } // Traverse the parent array and build the tree for ( int i = 0; i < n; i++) { // If the parent is -1, set the root // to the current node having // the value i which is stored in ref[i] if (parent[i] == -1) { root = ref[i]; } else { // Check if the parent's left child // is NULL then map the left child // to its parent. if (ref[parent[i]]->left == NULL) ref[parent[i]]->left = ref[i]; else ref[parent[i]]->right = ref[i]; } } // Return the root of the newly constructed tree return root; } // Function for inorder traversal void inorder(Node* root) { if (root != NULL) { inorder(root->left); cout << root->data << " " ; inorder(root->right); } } // Driver code int main() { int parent[] = { -1, 0, 0, 1, 1, 3, 5 }; int n = sizeof parent / sizeof parent[0]; Node* root = createTree(parent, n); cout << "Inorder Traversal of constructed tree\n" ; inorder(root); return 0; } |
Java
// Java program to construct a Binary Tree from parent array // A binary tree node class Node { int key; Node left, right; public Node() {} public Node( int key) { this .key = key; left = right = null ; } } class BinaryTree { Node root; // Function to construct binary tree from parent array. Node createTree( int parent[], int n) { // Create an array to store the reference // of all newly created nodes corresponding // to node value Node[] ref = new Node[n]; // This root represent the root of the // newly constructed tree Node root = new Node(); // Create n new tree nodes, each having // a value from 0 to n-1, and store them // in ref for ( int i = 0 ; i < n; i++) { Node temp = new Node(i); ref[i] = temp; } // Traverse the parent array and build the tree for ( int i = 0 ; i < n; i++) { // If the parent is -1, set the root // to the current node having // the value i which is stored in ref[i] if (parent[i] == - 1 ) { root = ref[i]; } else { // Check if the parent's left child // is NULL then map the left child // to its parent. if (ref[parent[i]].left == null ) ref[parent[i]].left = ref[i]; else ref[parent[i]].right = ref[i]; } } // Return the root of the newly constructed tree return root; } // function for inorder traversal void inorder(Node node) { if (node != null ) { inorder(node.left); System.out.print(node.key + " " ); inorder(node.right); } } // Driver code public static void main(String[] args) { BinaryTree tree = new BinaryTree(); int parent[] = new int [] { - 1 , 0 , 0 , 1 , 1 , 3 , 5 }; int n = parent.length; Node node = tree.createTree(parent, n); System.out.println( "Inorder traversal of constructed tree " ); tree.inorder(node); } } // This code has been contributed by Abhijeet Kumar(abhijeet19403) |
Python3
# Python program to construct a Binary Tree from parent array class Node: def __init__( self , x): self .data = x self .left = None self .right = None # Function to construct binary tree from parent array def createTree(parent, n): # Create an array to store the reference # of all newly created nodes corresponding # to node value ref = [] # This root refpresent the roof of the # newly constructed tree # create n new tree nodes, each having # a value from 0 to n-1, and store them in ref for i in range ( 0 , n): temp = Node(i) ref.append(temp) # Traverse the parent array and build the tree for i in range ( 0 , n): # If the parent is -1, set the root # to the current node having # the value i which is stored in ref[i] if parent[i] = = - 1 : root = ref[i] else : # check if the parent's left child # is NULL then map the left child # to its parent. if ref[parent[i]].left is None : ref[parent[i]].left = ref[i] else : ref[parent[i]].right = ref[i] # return the root of the newly constructed tree return root # Function for inorder traversal def inorder(root): if root is not None : inorder(root.left) print (root.data, end = " " ) inorder(root.right) # Driver code parent = [ - 1 , 0 , 0 , 1 , 1 , 3 , 5 ] n = 7 root = createTree(parent, n) print ( "Inorder traversal of constructed tree" ) inorder(root) # This code is contributed by Kirti Agarwal |
C#
// C# program to construct a Binary Tree from parent array using System; // A binary tree node class Node { public int key; public Node left, right; public Node() {} public Node( int key) { this .key = key; left = right = null ; } } class BinaryTree { public Node root; // Function to construct binary tree from parent array. public Node createTree( int [] parent, int n) { // Create an array to store the reference // of all newly created nodes corresponding // to node value Node[] refi = new Node[n]; // This root represent the root of the // newly constructed tree Node root = new Node(); // Create n new tree nodes, each having // a value from 0 to n-1, and store them // in ref for ( int i = 0; i < n; i++) { Node temp = new Node(i); refi[i] = temp; } // Traverse the parent array and build the tree for ( int i = 0; i < n; i++) { // If the parent is -1, set the root // to the current node having // the value i which is stored in ref[i] if (parent[i] == -1) { root = refi[i]; } else { // Check if the parent's left child // is NULL then map the left child // to its parent. if (refi[parent[i]].left == null ) refi[parent[i]].left = refi[i]; else refi[parent[i]].right = refi[i]; } } // Return the root of the newly constructed tree return root; } // function for inorder traversal public void inorder(Node node) { if (node != null ) { inorder(node.left); Console.Write(node.key + " " ); inorder(node.right); } } // Driver code public static void Main(String[] args) { BinaryTree tree = new BinaryTree(); int [] parent = new int [] { -1, 0, 0, 1, 1, 3, 5 }; int n = parent.Length; Node node = tree.createTree(parent, n); Console.WriteLine( "Inorder traversal of constructed tree " ); tree.inorder(node); } } // This code is contributed by lokeshpotta20. |
Javascript
// JavaScript Program to construct a Binary tree from parent array class Node{ constructor(x){ this .data = x; this .left = null ; this .right = null ; } } // Functiont to construct binary tree from parent array function createTree(parent, n){ // create an array to store the reference // of all newly created nodes corresponding // to node value let ref = []; // This root represent the root of the // newly constructed tree let root = new Node(); // create a new treenodes, each having // a value from 1 to n-1, and store them // in ref for (let i = 0; i<n; i++){ let temp = new Node(i); ref.push(temp); } // Traverse the parent array and build the tree for (let i = 0; i<n; i++){ // If the parent is -1, set the root // to the current node having // the value i which is stored in ref[i] if (parent[i] == -1){ root = ref[i]; } else { // check if the parent's left child // is NULL then map the left child // to its parent. if (ref[parent[i]].left == null ){ ref[parent[i]].left = ref[i]; } else { ref[parent[i]].right = ref[i]; } } } return root; } // Function for Inorder Traversal function inorder(root){ if (root != null ){ inorder(root.left); console.log(root.data + " " ); inorder(root.right); } } // Driver Code let parent = [-1, 0, 0, 1, 1, 3, 5]; let n = parent.length; let root = createTree(parent, n); console.log( "Inorder Traversal of constructed tree " ); inorder(root); // This code is contributed by Yash Agarwal(yashagarwal2852002) |
Inorder Traversal of constructed tree 6 5 3 1 4 0 2
Time Complexity: O(n), where n is the size of parent array
Auxiliary Space: O(n)
Similar Problem: Find Height of Binary Tree represented by Parent array
Please write comments if you find anything incorrect, or you want to share more information about the topic discussed above
Please Login to comment...