In Postorder traversal, we visit nodes in Left - Right - Node (LRN) order, which means each node is visited only after its left and right subtrees. Implementing this directly with Morris Traversal is tricky because we need to know when both subtrees are fully visited. To simplify, we use a mirrored Preorder approach: traverse the tree in Node - Right - Left (NRL) order, visiting each node when we first encounter it, then moving to the right subtree, and finally to the left subtree. During this traversal, we store the nodes in an array. Finally, by reversing the array, the NRL order becomes LRN, giving the correct Postorder sequence.
Morris Postorder Traversal Steps
Start with root Node(curr) and for each node:
If the node does not have a right child, visit(store) the node and move to the left child.
If the node has a right child, find the leftmost node in the right subtree.
If the leftmost node’s left is NULL. Make the current node as the left child of this leftmost node (temporary link).Visit (store) the current node and move to the right child.
If the leftmost node’s left points to the current node. Remove the temporary link (leftmost->left = NULL) and move to the left child.
Repeat until curr == NULL.
After traversal, reverse the stored array. This converts Node-Right-Left (NRL) order into Left-Right-Node (LRN) postorder.
C++
#include<algorithm>#include<iostream>#include<vector>usingnamespacestd;// Node StructureclassNode{public:intdata;Node*left;Node*right;Node(intdata){this->data=data;left=NULL;right=NULL;}};vector<int>postOrder(Node*root){vector<int>res;Node*current=root;while(current!=NULL){// If right child is null,// put the current node data// in res. Move to left child.if(current->right==NULL){res.push_back(current->data);current=current->left;}else{Node*predecessor=current->right;while(predecessor->left!=NULL&&predecessor->left!=current){predecessor=predecessor->left;}// If left child doesn't point// to this node, then put in res// this node and make left// child point to this nodeif(predecessor->left==NULL){res.push_back(current->data);predecessor->left=current;current=current->right;}// If the left child of inorder predecessor// already points to this nodeelse{predecessor->left=NULL;current=current->left;}}}// reverse the resreverse(res.begin(),res.end());returnres;}intmain(){// Constructing binary tree. // 1// / \ // 2 3// / \ // 4 5 Node*root=newNode(1);root->left=newNode(2);root->right=newNode(3);root->left->left=newNode(4);root->left->right=newNode(5);vector<int>ans=postOrder(root);for(autox:ans){cout<<x<<" ";}return0;}
C
#include<stdio.h>#include<stdlib.h>#define MAX_SIZE 100000// Node StructurestructNode{intdata;structNode*left;structNode*right;};// Reverse a segment of arrayvoidreverseArray(int*arr,intstart,intend){while(start<end){inttemp=arr[start];arr[start]=arr[end];arr[end]=temp;start++;end--;}}// Morris Postorder Traversalint*postOrder(structNode*root,int*size){structNode*curr=root;intcapacity=MAX_SIZE;int*res=(int*)malloc(capacity*sizeof(int));intcount=0;while(curr!=NULL){// If right child is null,// put the current node data// in res. Move to left child.if(curr->right==NULL){if(count>=capacity){capacity*=2;res=(int*)realloc(res,capacity*sizeof(int));}res[count++]=curr->data;curr=curr->left;}else{// Find the leftmost node in the right subtreestructNode*prev=curr->right;while(prev->left!=NULL&&prev->left!=curr){prev=prev->left;}// If the left child of inorder predecessor// already points to this nodeif(prev->left==curr){prev->left=NULL;curr=curr->left;}else{// If left child doesn't point// to this node, then put in res// this node and make left// child point to this nodeif(count>=capacity){capacity*=2;res=(int*)realloc(res,capacity*sizeof(int));}res[count++]=curr->data;prev->left=curr;curr=curr->right;}}}// Reverse the array to get correct postorder (LRN)reverseArray(res,0,count-1);*size=count;returnres;}// Helper to create a new nodestructNode*createNode(intdata){structNode*newNode=(structNode*)malloc(sizeof(structNode));newNode->data=data;newNode->left=NULL;newNode->right=NULL;returnnewNode;}intmain(){// Constructing binary tree:// 1// / \ // 2 3// / \ // 4 5 structNode*root=createNode(1);root->left=createNode(2);root->right=createNode(3);root->left->left=createNode(4);root->left->right=createNode(5);intsize;int*res=postOrder(root,&size);for(inti=0;i<size;i++){printf("%d ",res[i]);}free(res);return0;}
Java
importjava.util.ArrayList;importjava.util.Collections;// Node StructureclassNode{publicintdata;Nodeleft;Noderight;Node(intdata){this.data=data;left=null;right=null;}}classGFG{staticArrayList<Integer>postOrder(Noderoot){ArrayList<Integer>res=newArrayList<>();Nodecurrent=root;while(current!=null){// If right child is null,// put the current node data// in res. Move to left child.if(current.right==null){res.add(current.data);current=current.left;}else{Nodepredecessor=current.right;while(predecessor.left!=null&&predecessor.left!=current){predecessor=predecessor.left;}// If left child doesn't point// to this node, then put in res// this node and make left// child point to this nodeif(predecessor.left==null){res.add(current.data);predecessor.left=current;current=current.right;}// If the left child of inorder predecessor// already points to this nodeelse{predecessor.left=null;current=current.left;}}}// reverse the resCollections.reverse(res);returnres;}publicstaticvoidmain(String[]args){// Constructing binary tree. // 1// / \// 2 3// / \ // 4 5 Noderoot=newNode(1);root.left=newNode(2);root.right=newNode(3);root.left.left=newNode(4);root.left.right=newNode(5);ArrayList<Integer>ans=postOrder(root);for(intx:ans){System.out.print(x+" ");}}}
Python
# Node StructureclassNode:def__init__(self,data):self.data=dataself.left=Noneself.right=NonedefpostOrder(root):res=[]current=rootwhilecurrentisnotNone:# If right child is null,# put the current node data# in res. Move to left child.ifcurrent.rightisNone:res.append(current.data)current=current.leftelse:predecessor=current.rightwhilepredecessor.leftisnotNoneandpredecessor.left!=current:predecessor=predecessor.left# If left child doesn't point# to this node, then put in res# this node and make left# child point to this nodeifpredecessor.leftisNone:res.append(current.data)predecessor.left=currentcurrent=current.right# If the left child of inorder predecessor# already points to this nodeelse:predecessor.left=Nonecurrent=current.left# reverse the resres.reverse()returnresif__name__=="__main__":# Binary tree represenation# 1# / \# 2 3# / \ # 4 5 root=Node(1)root.left=Node(2)root.right=Node(3)root.left.left=Node(4)root.left.right=Node(5)ans=postOrder(root)forxinans:print(x,end=" ")
C#
usingSystem;usingSystem.Collections.Generic;// Node StructureclassNode{publicintdata;publicNodeleft;publicNoderight;publicNode(intdata){this.data=data;left=null;right=null;}}classGFG{staticList<int>postOrder(Noderoot){List<int>res=newList<int>();Nodecurrent=root;while(current!=null){// If right child is null,// put the current node data// in res. Move to left child.if(current.right==null){res.Add(current.data);current=current.left;}else{Nodepredecessor=current.right;while(predecessor.left!=null&&predecessor.left!=current){predecessor=predecessor.left;}// If left child doesn't point// to this node, then put in res// this node and make left// child point to this nodeif(predecessor.left==null){res.Add(current.data);predecessor.left=current;current=current.right;}// If the left child of inorder predecessor// already points to this nodeelse{predecessor.left=null;current=current.left;}}}// reverse the resres.Reverse();returnres;}staticvoidMain(string[]args){// Binary tree represenation// 1// / \// 2 3// / \ // 4 5 Noderoot=newNode(1);root.left=newNode(2);root.right=newNode(3);root.left.left=newNode(4);root.left.right=newNode(5);List<int>ans=postOrder(root);foreach(intxinans){Console.Write(x+" ");}}}
JavaScript
// Node StructureclassNode{constructor(data){this.data=data;this.left=null;this.right=null;}}functionpostOrder(root){letres=[];letcurrent=root;while(current!==null){// If right child is null,// put the current node data// in res. Move to left child.if(current.right===null){res.push(current.data);current=current.left;}else{letpredecessor=current.right;while(predecessor.left!==null&&predecessor.left!==current){predecessor=predecessor.left;}// If left child doesn't point// to this node, then put in res// this node and make left// child point to this nodeif(predecessor.left===null){res.push(current.data);predecessor.left=current;current=current.right;}// If the left child of inorder predecessor// already points to this nodeelse{predecessor.left=null;current=current.left;}}}// reverse the resres.reverse();returnres;}// Driver code// Binary tree represenation// 1// / \// 2 3// / \ // 4 5 letroot=newNode(1);root.left=newNode(2);root.right=newNode(3);root.left.left=newNode(4);root.left.right=newNode(5);letans=postOrder(root);for(letxofans){process.stdout.write(x+" ");}