GeeksforGeeks App
Open App
Browser
Continue

# Binary Tree Iterator for Inorder Traversal

Given a Binary Tree and an input array. The task is to create an Iterator that utilizes next() and hasNext() functions to perform Inorder traversal on the binary tree.

Examples:

Input:        8                          Input Array =  [next(), hasNext(), next(), next(), next(), hasNext(), next(), next(), hasNext()]
/   \
3     9
/   \
2     4
\
5

Output: [2, true, 3, 4, 5, true, 8, 9, false]
Explanation: According to in order traversal answer to the input array is calculated.
Inorder traversal = {2, 3, 4, 5, 8, 9}

Input:     4                           Input Array = [hasNext(), next(), next(), hasNext()]
/    \
3      2
\
1

Output: [true, 3, 4 true]

Naive Approach: A way is needed to traverse back to the ancestor once we reach the leaf node of the binary tree. A Stack data structure can be used for this.

Algorithm:

Class is Instantiated

1. initialize the stack
2. set current node = root
3. while current != NULL
2. current = current.left

hasNext() function

IF the stack is not empty

return true

ELSE

return false

next() function

• IF stack is empty (or hasNext() returns false)
• Throw an exception
• ELSE
• Initialize current = stack.top
• Pop the element from the stack
• If current.right != NULL
• Initialize next = current->right
• while next != NULL
• add next to the stack
• next = next.left
• return current

Below is the implementation of above approach

## C++

 `// CPP Program for above approach``#include ``#include ``using` `namespace` `std;` `// Structure of a Node``struct` `Node {``    ``int` `data;``    ``Node* left;``    ``Node* right;``};` `// Utility function to create a new Node``Node* newNode(``int` `data)``{``    ``Node* node = ``new` `Node;``    ``node->data = data;``    ``node->left = node->right = NULL;``    ``return` `node;``}` `// Inorder Iterator class``class` `InorderIterator {``private``:``    ``stack traversal;` `public``:``    ``InorderIterator(Node* root)``    ``{``        ``moveLeft(root);``    ``}` `    ``void` `moveLeft(Node* current)``    ``{``        ``while` `(current) {``            ``traversal.push(current);``            ``current = current->left;``        ``}``    ``}` `    ``bool` `hasNext()``    ``{``        ``return` `!traversal.empty();``    ``}` `    ``Node* next()``    ``{``        ``if` `(!hasNext())``            ``throw` `"No such element Exists"``;` `        ``Node* current = traversal.top();``        ``traversal.pop();` `        ``if` `(current->right)``            ``moveLeft(current->right);` `        ``return` `current;``    ``}``};` `// Driver Code``int` `main()``{``    ``Node* root = newNode(8);``    ``root->right = newNode(9);``    ``root->left = newNode(3);``    ``root->left->left = newNode(2);``    ``root->left->right = newNode(4);``    ``root->left->right->right = newNode(5);` `    ``InorderIterator itr(root);``    ``try` `{``        ``cout << itr.next()->data << ``" "``;``        ``cout << itr.hasNext() << ``" "``;``        ``cout << itr.next()->data << ``" "``;``        ``cout << itr.next()->data << ``" "``;``        ``cout << itr.next()->data << ``" "``;``        ``cout << itr.hasNext() << ``" "``;``        ``cout << itr.next()->data << ``" "``;``        ``cout << itr.next()->data << ``" "``;``        ``cout << itr.hasNext() << ``" "``;``    ``}``    ``catch` `(``const` `char``* msg) {``        ``cout << msg;``    ``}``    ``return` `0;``}` `// This code is contributed by adityamaharshi21`

## Java

 `// Java Program for above approach``import` `java.util.*;` `// Structure of a Node``class` `Node {``    ``int` `data;``    ``Node left;``    ``Node right;` `    ``Node(``int` `data)``    ``{``        ``this``.data = data;``        ``left = right = ``null``;``    ``}``}` `// Inorder Iterator class``class` `InorderIterator {``    ``private` `Stack traversal;` `    ``InorderIterator(Node root)``    ``{``        ``traversal = ``new` `Stack();``        ``moveLeft(root);``    ``}` `    ``private` `void` `moveLeft(Node current)``    ``{``        ``while` `(current != ``null``) {``            ``traversal.push(current);``            ``current = current.left;``        ``}``    ``}` `    ``public` `boolean` `hasNext()``    ``{``        ``return` `!traversal.isEmpty();``    ``}` `    ``public` `Node next()``    ``{``        ``if` `(!hasNext())``            ``throw` `new` `NoSuchElementException();` `        ``Node current = traversal.pop();` `        ``if` `(current.right != ``null``)``            ``moveLeft(current.right);` `        ``return` `current;``    ``}``}` `// Class to Test given set of inputs``class` `Test {` `    ``// Driver Code``    ``public` `static` `void` `main(String args[])``    ``{``        ``Node root = ``new` `Node(``8``);``        ``root.right = ``new` `Node(``9``);``        ``root.left = ``new` `Node(``3``);``        ``root.left.left = ``new` `Node(``2``);``        ``root.left.right = ``new` `Node(``4``);``        ``root.left.right.right = ``new` `Node(``5``);` `        ``InorderIterator itr = ``new` `InorderIterator(root);``        ``try` `{``            ``System.out.print(itr.next().data + ``" "``);``            ``System.out.print(itr.hasNext() + ``" "``);``            ``System.out.print(itr.next().data + ``" "``);``            ``System.out.print(itr.next().data + ``" "``);``            ``System.out.print(itr.next().data + ``" "``);``            ``System.out.print(itr.hasNext() + ``" "``);``            ``System.out.print(itr.next().data + ``" "``);``            ``System.out.print(itr.next().data + ``" "``);``            ``System.out.print(itr.hasNext() + ``" "``);``        ``}``        ``catch` `(NoSuchElementException e) {``            ``System.out.print(``"No such element Exists"``);``        ``}``    ``}``}`

## Python

 `# Python Program for above approach``class` `Node:``    ``def` `__init__(``self``, data):``        ``self``.data ``=` `data``        ``self``.left ``=` `None``        ``self``.right ``=` `None` `# Inorder Iterator class``class` `InorderIterator:``    ``def` `__init__(``self``, root):``        ``self``.traversal ``=` `[]``        ``self``.moveLeft(root)` `    ``def` `moveLeft(``self``, current):``        ``while` `current !``=` `None``:``            ``self``.traversal.append(current)``            ``current ``=` `current.left` `    ``def` `hasNext(``self``):``        ``return` `len``(``self``.traversal) > ``0` `    ``def` `next``(``self``):``        ``if` `not` `self``.hasNext():``            ``raise` `Exception(``'No such element Exists'``)` `        ``current ``=` `self``.traversal.pop()` `        ``if` `current.right !``=` `None``:``            ``self``.moveLeft(current.right)` `        ``return` `current` `# Class to Test given set of inputs` `# Driver Code``root ``=` `Node(``8``)``root.right ``=` `Node(``9``)``root.left ``=` `Node(``3``)``root.left.left ``=` `Node(``2``)``root.left.right ``=` `Node(``4``)``root.left.right.right ``=` `Node(``5``)` `itr ``=` `InorderIterator(root)``try``:``    ``print``(itr.``next``().data)``    ``print``(itr.hasNext())``    ``print``(itr.``next``().data)``    ``print``(itr.``next``().data)``    ``print``(itr.``next``().data)``    ``print``(itr.hasNext())``    ``print``(itr.``next``().data)``    ``print``(itr.``next``().data)``    ``print``(itr.hasNext())``except` `Exception as e:``    ``print``(``"No such element Exists"``)``    ` `# This code is contributed by adityamaharshi21`

## C#

 `// C# code for the above approach``using` `System;``using` `System.Collections.Generic;` `// Structure of a Node``class` `Node``{``  ``public` `int` `Data { ``get``; ``set``; }``  ``public` `Node Left { ``get``; ``set``; }``  ``public` `Node Right { ``get``; ``set``; }` `  ``public` `Node(``int` `data)``  ``{``    ``Data = data;``    ``Left = Right = ``null``;``  ``}``}` `// Inorder Iterator class``class` `InorderIterator``{``  ``private` `Stack traversal;` `  ``public` `InorderIterator(Node root)``  ``{``    ``traversal = ``new` `Stack();``    ``MoveLeft(root);``  ``}` `  ``private` `void` `MoveLeft(Node current)``  ``{``    ``while` `(current != ``null``)``    ``{``      ``traversal.Push(current);``      ``current = current.Left;``    ``}``  ``}` `  ``public` `bool` `HasNext()``  ``{``    ``return` `traversal.Count > 0;``  ``}` `  ``public` `Node Next()``  ``{``    ``if` `(!HasNext())``      ``throw` `new` `InvalidOperationException(``"No more elements in the inorder traversal."``);` `    ``Node current = traversal.Pop();` `    ``if` `(current.Right != ``null``)``      ``MoveLeft(current.Right);` `    ``return` `current;``  ``}``}` `// Class to Test given set of inputs``class` `GFG``{``  ``// Driver Code``  ``static` `void` `Main(``string``[] args)``  ``{``    ``Node root = ``new` `Node(8);``    ``root.Right = ``new` `Node(9);``    ``root.Left = ``new` `Node(3);``    ``root.Left.Left = ``new` `Node(2);``    ``root.Left.Right = ``new` `Node(4);``    ``root.Left.Right.Right = ``new` `Node(5);` `    ``InorderIterator itr = ``new` `InorderIterator(root);``    ``try``    ``{``      ``Console.Write(itr.Next().Data + ``" "``);``      ``Console.Write(itr.HasNext() + ``" "``);``      ``Console.Write(itr.Next().Data + ``" "``);``      ``Console.Write(itr.Next().Data + ``" "``);``      ``Console.Write(itr.Next().Data + ``" "``);``      ``Console.Write(itr.HasNext() + ``" "``);``      ``Console.Write(itr.Next().Data + ``" "``);``      ``Console.Write(itr.Next().Data + ``" "``);``      ``Console.Write(itr.HasNext() + ``" "``);``    ``}``    ``catch` `(InvalidOperationException e)``    ``{``      ``Console.Write(``"No such element Exists"``);``    ``}``  ``}``}` `// This code is contributed by Potta Lokesh`

## Javascript

 `// Javascript Program for above approach``class Node {``    ``constructor(data) {``        ``this``.data = data;``        ``this``.left = ``null``;``        ``this``.right = ``null``;``    ``}``}` `// Inorder Iterator class``class InorderIterator {``    ``constructor(root) {``        ``this``.traversal = [];``        ``this``.moveLeft(root);``    ``}` `    ``moveLeft(current) {``        ``while` `(current != ``null``) {``            ``this``.traversal.push(current);``            ``current = current.left;``        ``}``    ``}` `    ``hasNext() {``        ``return` `this``.traversal.length > 0;``    ``}` `    ``next() {``        ``if` `(!``this``.hasNext())``            ``throw` `new` `Error(``'No such element Exists'``);` `        ``let current = ``this``.traversal.pop();` `        ``if` `(current.right != ``null``)``            ``this``.moveLeft(current.right);` `        ``return` `current;``    ``}``}` `// Class to Test given set of inputs`  `// Driver Code``let root = ``new` `Node(8);``root.right = ``new` `Node(9);``root.left = ``new` `Node(3);``root.left.left = ``new` `Node(2);``root.left.right = ``new` `Node(4);``root.left.right.right = ``new` `Node(5);` `let itr = ``new` `InorderIterator(root);``try` `{``    ``console.log(itr.next().data + ``" "``);``    ``console.log(itr.hasNext() + ``" "``);``    ``console.log(itr.next().data + ``" "``);``    ``console.log(itr.next().data + ``" "``);``    ``console.log(itr.next().data + ``" "``);``    ``console.log(itr.hasNext() + ``" "``);``    ``console.log(itr.next().data + ``" "``);``    ``console.log(itr.next().data + ``" "``);``    ``console.log(itr.hasNext() + ``" "``);``}``catch` `(e) {``    ``console.log(``"No such element Exists"``);``}` `// This code is contributed by adityamaharshi21`

Output

`2 true 3 4 5 true 8 9 false `

Time Complexity: O(N), Where N is the number of nodes in the binary tree.
Auxiliary Space: O(N), The Stack will hold all N elements in the worst case.

Efficient Approach: Morris Traversal can be used to solve this question using constant space. The idea behind morris traversal is to create a temporary link between a node and the right-most node in its left sub-tree so that the ancestor node can be backtracked. A reference of the ancestor node is set to the right child of the right-most node in its left sub-tree.

Algorithm:

Class is Instantiated

Initialize current = root and rightMost = NULL

hasNext() function

IF current != NULL

return true

ELSE

return false

next() function

• IF current = NULL ( or hasNext() returns false)
• Throw an exception
• ELSE
• IF current.left = NULL
• Initialize temp = current
• current = current.right
• return temp
• ELSE
• Initialize rightMost = current->left
• while rightMost.right != NULL && rightMost.right != current
• rightMost = rightMost.right
• IF rightMost.right == NULL
• rightMost.right = current
• current = current.left
• ELSE
• temp = current
• rightMost.right = null
• current = current.right
• return current
• Call the function again

Below is the implementation of above approach.

## C++

 `#include ``#include ` `struct` `Node {``    ``int` `data;``    ``Node *left, *right;` `    ``Node(``int` `data) {``        ``this``->data = data;``        ``this``->left = ``this``->right = NULL;``    ``}``};` `class` `InorderIterator {``private``:``    ``Node *current, *rightMost;``public``:``    ``InorderIterator(Node *root) {``        ``current = root;``        ``rightMost = NULL;``    ``}` `    ``bool` `hasNext() { ``return` `current != NULL; }` `    ``Node* next() {``        ``if` `(!hasNext()) {``            ``std::cout << ``"No such element exists"` `<< std::endl;``            ``return` `NULL;``        ``}` `        ``if` `(current->left == NULL) {``            ``Node *temp = current;``            ``current = current->right;``            ``return` `temp;``        ``}` `        ``rightMost = current->left;` `        ``while` `(rightMost->right != NULL``               ``&& rightMost->right != current) {``            ``rightMost = rightMost->right;``        ``}` `        ``if` `(rightMost->right == NULL) {``            ``rightMost->right = current;``            ``current = current->left;``        ``} ``else` `{``            ``rightMost->right = NULL;``            ``Node *temp = current;``            ``current = current->right;``            ``return` `temp;``        ``}` `        ``return` `next();``    ``}``};` `int` `main() {``    ``Node *root = ``new` `Node(8);``    ``root->right = ``new` `Node(9);``    ``root->left = ``new` `Node(3);``    ``root->left->left = ``new` `Node(2);``    ``root->left->right = ``new` `Node(4);``    ``root->left->right->right = ``new` `Node(5);` `    ``InorderIterator itr(root);``    ``std::cout << itr.next()->data << ``" "``;``    ``std::cout << itr.hasNext() << ``" "``;``    ``std::cout << itr.next()->data << ``" "``;``    ``std::cout << itr.next()->data << ``" "``;``    ``std::cout << itr.next()->data << ``" "``;``    ``std::cout << itr.hasNext() << ``" "``;``    ``std::cout << itr.next()->data << ``" "``;``    ``std::cout << itr.next()->data << ``" "``;``    ``std::cout << itr.hasNext() << ``" "``;``    ``return` `0;``}` `// This code is contributed by anskalyan3.`

## Java

 `// Java Program for above approach``import` `java.util.*;` `// Structure of a Node``class` `Node {``    ``int` `data;``    ``Node left;``    ``Node right;` `    ``Node(``int` `data)``    ``{``        ``this``.data = data;``        ``left = right = ``null``;``    ``}``}` `// Inorder Iterator class``class` `InorderIterator {``    ``private` `Node current, rightMost;` `    ``InorderIterator(Node root)``    ``{``        ``current = root;``        ``rightMost = ``null``;``    ``}` `    ``public` `boolean` `hasNext() { ``return` `current != ``null``; }` `    ``public` `Node next()``    ``{``        ``if` `(!hasNext())``            ``throw` `new` `NoSuchElementException();` `        ``if` `(current.left == ``null``) {``            ``Node temp = current;``            ``current = current.right;``            ``return` `temp;``        ``}` `        ``rightMost = current.left;` `        ``while` `(rightMost.right != ``null``               ``&& rightMost.right != current)``            ``rightMost = rightMost.right;` `        ``if` `(rightMost.right == ``null``) {``            ``rightMost.right = current;``            ``current = current.left;``        ``}` `        ``else` `{``            ``rightMost.right = ``null``;``            ``Node temp = current;``            ``current = current.right;``            ``return` `temp;``        ``}` `        ``return` `next();``    ``}``}` `class` `Test {` `    ``// Driver Code``    ``public` `static` `void` `main(String args[])``    ``{``        ``Node root = ``new` `Node(``8``);``        ``root.right = ``new` `Node(``9``);``        ``root.left = ``new` `Node(``3``);``        ``root.left.left = ``new` `Node(``2``);``        ``root.left.right = ``new` `Node(``4``);``        ``root.left.right.right = ``new` `Node(``5``);` `        ``InorderIterator itr = ``new` `InorderIterator(root);``        ``try` `{``            ``System.out.print(itr.next().data + ``" "``);``            ``System.out.print(itr.hasNext() + ``" "``);``            ``System.out.print(itr.next().data + ``" "``);``            ``System.out.print(itr.next().data + ``" "``);``            ``System.out.print(itr.next().data + ``" "``);``            ``System.out.print(itr.hasNext() + ``" "``);``            ``System.out.print(itr.next().data + ``" "``);``            ``System.out.print(itr.next().data + ``" "``);``            ``System.out.print(itr.hasNext() + ``" "``);``        ``}``        ``catch` `(NoSuchElementException e) {``            ``System.out.print(``"No such element Exists"``);``        ``}``    ``}``}`

## Python

 `class` `Node:``    ``def` `__init__(``self``, data):``        ``self``.data ``=` `data``        ``self``.left ``=` `self``.right ``=` `None`  `class` `InorderIterator:``    ``def` `__init__(``self``, root):``        ``self``.current ``=` `root``        ``self``.right_most ``=` `None` `    ``def` `has_next(``self``):``        ``return` `self``.current ``is` `not` `None` `    ``def` `next``(``self``):``        ``if` `not` `self``.has_next():``            ``print``(``"No such element exists"``)``            ``return` `None` `        ``if` `self``.current.left ``is` `None``:``            ``temp ``=` `self``.current``            ``self``.current ``=` `self``.current.right``            ``return` `temp` `        ``self``.right_most ``=` `self``.current.left` `        ``while` `self``.right_most.right ``is` `not` `None` `and` `self``.right_most.right !``=` `self``.current:``            ``self``.right_most ``=` `self``.right_most.right` `        ``if` `self``.right_most.right ``is` `None``:``            ``self``.right_most.right ``=` `self``.current``            ``self``.current ``=` `self``.current.left``        ``else``:``            ``self``.right_most.right ``=` `None``            ``temp ``=` `self``.current``            ``self``.current ``=` `self``.current.right``            ``return` `temp` `        ``return` `self``.``next``()`  `root ``=` `Node(``8``)``root.right ``=` `Node(``9``)``root.left ``=` `Node(``3``)``root.left.left ``=` `Node(``2``)``root.left.right ``=` `Node(``4``)``root.left.right.right ``=` `Node(``5``)` `itr ``=` `InorderIterator(root)``print``(itr.``next``().data)``print``(itr.has_next())``print``(itr.``next``().data)``print``(itr.``next``().data)``print``(itr.``next``().data)``print``(itr.has_next())``print``(itr.``next``().data)``print``(itr.``next``().data)``print``(itr.has_next())`

## Javascript

 `// JavaScript program for above approach``class Node {``    ``constructor(data) {``        ``this``.data = data;``        ``this``.left = ``null``;``        ``this``.right = ``null``;``    ``}``}` `class InorderIterator {``    ``constructor(root) {``        ``this``.current = root;``        ``this``.rightMost = ``null``;``    ``}` `    ``hasNext() { ``return` `this``.current != ``null``; }` `    ``next() {``        ``if` `(!``this``.hasNext())``            ``throw` `new` `Error(``"No such element Exists"``);` `        ``if` `(``this``.current.left == ``null``) {``            ``let temp = ``this``.current;``            ``this``.current = ``this``.current.right;``            ``return` `temp;``        ``}` `        ``this``.rightMost = ``this``.current.left;` `        ``while` `(``this``.rightMost.right != ``null``               ``&& ``this``.rightMost.right != ``this``.current)``            ``this``.rightMost = ``this``.rightMost.right;` `        ``if` `(``this``.rightMost.right == ``null``) {``            ``this``.rightMost.right = ``this``.current;``            ``this``.current = ``this``.current.left;``        ``}` `        ``else` `{``            ``this``.rightMost.right = ``null``;``            ``let temp = ``this``.current;``            ``this``.current = ``this``.current.right;``            ``return` `temp;``        ``}` `        ``return` `this``.next();``    ``}``}` `let root = ``new` `Node(8);``root.right = ``new` `Node(9);``root.left = ``new` `Node(3);``root.left.left = ``new` `Node(2);``root.left.right = ``new` `Node(4);``root.left.right.right = ``new` `Node(5);` `let itr = ``new` `InorderIterator(root);``try` `{``    ``console.log(itr.next().data + ``" "``);``    ``console.log(itr.hasNext() + ``" "``);``    ``console.log(itr.next().data + ``" "``);``    ``console.log(itr.next().data + ``" "``);``    ``console.log(itr.next().data + ``" "``);``    ``console.log(itr.hasNext() + ``" "``);``    ``console.log(itr.next().data + ``" "``);``    ``console.log(itr.next().data + ``" "``);``    ``console.log(itr.hasNext() + ``" "``);``}``catch` `(e) {``    ``console.log(``"No such element Exists"``);``}` `// This code is contributed by adityamaharshi21`

## C#

 `// C# Program for above approach` `using` `System;``using` `System.Collections.Generic;` `// Structure of a Node``public` `class` `Node {``    ``public` `int` `data;``    ``public` `Node left, right;``    ``public` `Node(``int` `data)``    ``{``        ``this``.data = data;``        ``left = right = ``null``;``    ``}``}` `// Inorder Iterator class``public` `class` `InorderIterator {``    ``private` `Node current, rightMost;``    ``public` `InorderIterator(Node root)``    ``{``        ``current = root;``        ``rightMost = ``null``;``    ``}` `    ``public` `bool` `HasNext() { ``return` `current != ``null``; }` `    ``public` `Node Next()``    ``{``        ``if` `(!HasNext())``            ``throw` `new` `Exception(``"No such element exists"``);` `        ``if` `(current.left == ``null``) {``            ``Node temp = current;``            ``current = current.right;``            ``return` `temp;``        ``}` `        ``rightMost = current.left;` `        ``while` `(rightMost.right != ``null``               ``&& rightMost.right != current)``            ``rightMost = rightMost.right;` `        ``if` `(rightMost.right == ``null``) {``            ``rightMost.right = current;``            ``current = current.left;``        ``}` `        ``else` `{``            ``rightMost.right = ``null``;``            ``Node temp = current;``            ``current = current.right;``            ``return` `temp;``        ``}` `        ``return` `Next();``    ``}``}` `public` `class` `GFG {` `    ``static` `public` `void` `Main()``    ``{` `        ``// Code``        ``Node root = ``new` `Node(8);``        ``root.right = ``new` `Node(9);``        ``root.left = ``new` `Node(3);``        ``root.left.left = ``new` `Node(2);``        ``root.left.right = ``new` `Node(4);``        ``root.left.right.right = ``new` `Node(5);` `        ``InorderIterator itr = ``new` `InorderIterator(root);``        ``try` `{``            ``Console.Write(itr.Next().data + ``" "``);``            ``Console.Write(itr.HasNext() + ``" "``);``            ``Console.Write(itr.Next().data + ``" "``);``            ``Console.Write(itr.Next().data + ``" "``);``            ``Console.Write(itr.Next().data + ``" "``);``            ``Console.Write(itr.HasNext() + ``" "``);``            ``Console.Write(itr.Next().data + ``" "``);``            ``Console.Write(itr.Next().data + ``" "``);``            ``Console.Write(itr.HasNext() + ``" "``);``        ``}``        ``catch` `(Exception e) {``            ``Console.Write(``"No such element Exists"``);``        ``}``    ``}``}` `// This code is contributed by karthik`

Output

`2 true 3 4 5 true 8 9 false `

Time Complexity: O(N), where N is the number of nodes in the binary tree. Although we are creating temporary links are created and nodes are traversed multiple times (at most 3 times), the time complexity is still linear.
Auxiliary Space: O(1)

My Personal Notes arrow_drop_up