Wednesday 20 September 2023

Maximum width of binary tree is defined as maximum number of nodes that can occur between two extreme nodes in any level (code in JAVA)


import java.util.*;


import javax.swing.tree.TreeNode;


public class test {

    static class Node {

        int data;

        Node left;

        Node right;

        int hd;


        public Node(int data) {

            this.data = data;

            this.left = null;

            this.right = null;

            hd = 0;

        }

    }



    static class BinaryTree {

        static Node buildTree(Scanner scanner, String position, int parentValue) {

            System.out.print("Add " + position + " node for " + parentValue + " (y/n): ");

            String userChoice = scanner.next();


            if (userChoice.equalsIgnoreCase("y")) {

                System.out.print("Enter " + position + " node value: ");

                int nodeValue = scanner.nextInt();

                Node newNode = new Node(nodeValue);


                newNode.left = buildTree(scanner, "left", nodeValue);

                newNode.right = buildTree(scanner, "right", nodeValue);


                return newNode;

            } else {

                return null;

            }

        }

    }

    //levelorder traversal

    public static void levelorder(Node root)

    {

        if(root==null) return;

        Queue<Node> q = new LinkedList<>();

        q.add(root);

        q.add(null);

        while(!q.isEmpty())

        {

            Node currnode = q.remove();

            if(currnode==null) //NULL DENOTES NEW LINE

            {

                System.out.println();

                if(q.isEmpty())

                {

                    break;

                }

                else

                {

                    q.add(null);

                }

            }

            else

            {

                System.out.print(currnode.data+" ");

                if(currnode.left!=null)

                {

                    q.add(currnode.left);

                }

                if(currnode.right!=null)

                {

                    q.add(currnode.right);

                }

            }

        }

    }


    public static ArrayList<Integer> preorderUsingStack(Node root)

    {

        ArrayList<Integer> preorderArrayList = new ArrayList<Integer>();

        if (root==null) return preorderArrayList;

        Stack<Node> st = new Stack<Node>();

        st.push(root);

        while(!st.isEmpty())

        {

            root = st.pop();

            preorderArrayList.add(root.data);

            if(root.right != null)

            {

                st.push(root.right);

            }

            if(root.left != null)

            {

                st.push(root.left);

            }


        }

        return preorderArrayList;

    }


    public static ArrayList<Integer> inorderUsingStack(Node root)

    {

        ArrayList<Integer> inorderArrayList = new ArrayList<Integer>();

        if (root == null) return null;

        Stack<Node> st = new Stack<Node>();

        Node node = root;

        while(true)

        {

            if(node != null)

            {

                st.push(node);

                node = node.left;

            }

            else

            {

                if(st.isEmpty())

                {

                    break;

                }

                node = st.pop();

                inorderArrayList.add(node.data);

                node = node.right;

            }

        }

        return inorderArrayList;

    }


    public static ArrayList<Integer> postorderUsing2Stack(Node root)

    {

        ArrayList<Integer> postorderArrayList = new ArrayList<Integer>();

        if(root == null){return postorderArrayList;}

        Stack<Node> st1 = new Stack<Node>();

        Stack<Node> st2 = new Stack<Node>();

        st1.push(root);

        while(!st1.isEmpty())

        {

            root = st1.pop();

            st2.push(root);

            if(root.left!=null) st1.push(root.left);

            if(root.right!=null) st1.push(root.right);

        }

        while(!st2.isEmpty())

        {

            postorderArrayList.add(st2.pop().data);

        }

        return postorderArrayList;

    }


    public static ArrayList<Integer> postorderUsing1Stack(Node root) {

        ArrayList<Integer> postorderArrayList = new ArrayList<Integer>();

        if (root == null) return postorderArrayList;

        Stack<Node> st = new Stack<Node>();

        Node curr = root;

        Node prev = null;

        

        while (curr != null || !st.isEmpty()) {

            if (curr != null) {

                st.push(curr);

                curr = curr.left;

            } else {

                Node peekNode = st.peek();

                if (peekNode.right == null || peekNode.right == prev) { //peekNode is topNode in stack

                    postorderArrayList.add(peekNode.data);

                    prev = peekNode;

                    st.pop();

                } else {

                    curr = peekNode.right;

                }

            }

        }

        

        return postorderArrayList;

    }


    static class node_numOfTraversal_pair

    {

        Node node;

        int num;

        

        public node_numOfTraversal_pair(Node root, int _num)

        {

            this.num = _num;

            this.node = root;

        }

    }


    public static void preInPost_traversal_in_one(Node root, ArrayList<Integer> preorderArrayList, ArrayList<Integer> inorderArrayList, ArrayList<Integer> postorderArrayList)

    {

        Stack<node_numOfTraversal_pair> st = new Stack<node_numOfTraversal_pair>();

        if(root == null) return;

        // or instead of above two lines you can directly write as below

        // node_numOfTraversal_pair pair = new node_numOfTraversal_pair(root,1);

        // st.push(pair);

        st.push(new node_numOfTraversal_pair(root, 1));

        while(!st.isEmpty())

        {

            node_numOfTraversal_pair it = st.pop();

            // this is part of pre

            // increment 1 to 2 

            // push the left side of the tree

            if(it.num == 1)

            {

                preorderArrayList.add(it.node.data);

                it.num++;

                st.push(it);

                if(it.node.left != null)

                {

                    st.push(new node_numOfTraversal_pair(it.node.left, 1));


                }

            }

            // this is a part of in 

            // increment 2 to 3 

            // push right

            else if(it.num == 2)

            {

                inorderArrayList.add(it.node.data);

                it.num++;

                st.push(it);

                if(it.node.right != null)

                {

                    st.push(new node_numOfTraversal_pair(it.node.right, 1));

                }

            }

            // don't push it back again 

            else    

            {

                postorderArrayList.add(it.node.data);

            }

        }


    }


    public static int maxDepthOfBinaryTree(Node root)

    {

        if(root == null) return 0;


        int leftHeight = maxDepthOfBinaryTree(root.left);

        int rightHeight = maxDepthOfBinaryTree(root.right);

        return 1 + Math.max(leftHeight,rightHeight);

    }


    // To check for Balanced Binary Tree

    public static int isBalacedBinaryTree(Node root)

    {

        if(root == null) return 0;


        int leftHeight = isBalacedBinaryTree(root.left);

        if(leftHeight==-1){return -1;}

        int rightHeight = isBalacedBinaryTree(root.right);

        if(rightHeight==-1){return -1;}

        if(Math.abs(leftHeight-rightHeight)>1){return -1;}

        return 1 + Math.max(leftHeight,rightHeight);

    }

    public static boolean isBalancedBinaryTree_boolean_value(Node root)

    {

        return isBalacedBinaryTree(root) != -1;

    }


    // To measure diameter of binary tree

    public static int height(Node root, int diameter[])

    {

        if(root == null) return 0;


        int leftHeight = height(root.left,diameter);

        int rightHeight = height(root.right,diameter);

        diameter[0] = Math.max(diameter[0],leftHeight+rightHeight);

        return 1 + Math.max(leftHeight,rightHeight);

    }

    public static int diameterofbinarytree(Node root)

    {

        int diameter1[]= new int[1];

        height(root,diameter1);

        return diameter1[0];

    }


    // Maximum Path Sum

    public static int maxPath(Node node, int maxValue[]) {

        if (node == null) return 0;

        int left = Math.max(0, maxPath(node.left, maxValue));

        int right = Math.max(0, maxPath(node.right, maxValue));

        maxValue[0] = Math.max(maxValue[0], left + right + node.data);

        return Math.max(left, right) + node.data;

    }

    public static int maxPathSum(Node root) {

        int maxValue[] = new int[1];

        maxValue[0] = Integer.MIN_VALUE;

        maxPath(root, maxValue);

        return maxValue[0];

    }


    // Zig-zag or spiral traversal 

    static ArrayList<Integer> zigZagTraversal(Node root)

    {

        ArrayList<Integer> ans = new ArrayList<Integer>();

        if (root == null)

            return ans;

        Queue<Node> q = new LinkedList<Node>();

        q.add(root);

        boolean leftToRight = true;

        while (q.size() > 0) {

            int size = q.size();

            ArrayList<Integer> temp = new ArrayList<>();

            for (int i = 0; i < size; i++) {

                Node curr = q.poll();

                if (curr.left != null)

                    q.add(curr.left);

                if (curr.right != null)

                    q.add(curr.right);

                temp.add(curr.data);

            }

            if (leftToRight) 

            {

                // do nothing

            }

            else {

                Collections.reverse(temp);

            }

            for (int i = 0; i < temp.size(); i++) {

                ans.add(temp.get(i));

            }

            leftToRight = !(leftToRight);

        }

        return ans;

    }


    // boundary traversal

     public static void printLeftBoundary(Node node) {

        if (node == null)

            return;

        if (node.left != null) {

            System.out.print(node.data + " ");

            printLeftBoundary(node.left);

        } else if (node.right != null) {

            System.out.print(node.data + " ");

            printLeftBoundary(node.right);

        }

    }


    public static void printRightBoundary(Node node) {

        if (node == null)

            return;

        if (node.right != null) {

            printRightBoundary(node.right);

            System.out.print(node.data + " ");

        } else if (node.left != null) {

            printRightBoundary(node.left);

            System.out.print(node.data + " ");

        }

    }


    public static void printLeaves(Node node) {

        if (node == null)

            return;


        printLeaves(node.left);

        if (node.left == null && node.right == null)

            System.out.print(node.data + " ");

        printLeaves(node.right);

    }


    public static void boundaryTraversal(Node root) {

        if (root == null)

            return;

        System.out.print(root.data + " ");

        printLeftBoundary(root.left);

        printLeaves(root.left);

        printLeaves(root.right);

        printRightBoundary(root.right);

    }


    // Vertical order traversal

    public static void verticalOrder(Node root,int horizontal_dist, Map<Integer, Vector<Integer>> m)

    {

        if (root==null) return;

        Vector<Integer> v = m.get(horizontal_dist);

        if(v==null)

        {

            v = new Vector<Integer>();

            v.add(root.data);

        }

        else

        {

            v.add(root.data);

        }

        m.put(horizontal_dist,v);

        verticalOrder(root.left, horizontal_dist - 1, m);

        verticalOrder(root.right, horizontal_dist + 1, m);

    }


    // Top-view of a binary tree

    static class Pair {

        Node node;

        int hd;

    

        Pair(Node node, int hd) {

            this.node = node;

            this.hd = hd;

        }

    }

    

    static ArrayList<Integer> topView(Node root)

    {

        ArrayList<Integer> ans = new ArrayList<>(); 

        if(root == null) return ans;

        Map<Integer, Integer> map = new TreeMap<>();

        Queue<Pair> q = new LinkedList<Pair>();

        q.add(new Pair(root, 0)); 

        while(!q.isEmpty()) {

            Pair it = q.remove();

            int hd = it.hd; 

            Node temp = it.node; 

            if(map.get(hd) == null) map.put(hd, temp.data); 

            if(temp.left != null) {

                

                q.add(new Pair(temp.left, hd - 1)); 

            }

            if(temp.right != null) {

                

                q.add(new Pair(temp.right, hd + 1)); 

            }

        }

    

        for (Map.Entry<Integer,Integer> entry : map.entrySet()) {

            ans.add(entry.getValue()); 

        }

        return ans; 

    }


    // Bottom-View of Binary Tree

   

    public static ArrayList <Integer> bottomView(Node root)

    {

        ArrayList<Integer> ans = new ArrayList<>(); 

        if(root == null) return ans;

        Map<Integer, Integer> map = new TreeMap<>();

        Queue<Node> q = new LinkedList<Node>();

        root.hd = 0;

        q.add(root); 

        while(!q.isEmpty()) {

            Node temp = q.remove();

            int hd = temp.hd; 

            map.put(hd, temp.data); 

            if(temp.left != null) {

                temp.left.hd = hd - 1; 

                q.add(temp.left); 

            }

            if(temp.right != null) {

                temp.right.hd = hd + 1; 

                q.add(temp.right); 

            }

        }

        

        for (Map.Entry<Integer,Integer> entry : map.entrySet()) {

            ans.add(entry.getValue()); 

        }

        return ans; 

    }


    // Right View of binary tree

    public static List<Integer> rightSideView(Node root) {

        List<Integer> result = new ArrayList<Integer>();

        rightView(root, result, 0);

        return result;

    }

    

    public static void rightView(Node curr, List<Integer> result, int currDepth){

        if(curr == null){

            return;

        }

        if(currDepth == result.size()){

            result.add(curr.data);

        }

        

        rightView(curr.right, result, currDepth + 1);

        rightView(curr.left, result, currDepth + 1);

        

    }

    //Left-side view

    public static List<Integer> leftSideView(Node root) {

        List<Integer> result = new ArrayList<Integer>();

        leftView(root, result, 0);

        return result;

    }

    

    public static void leftView(Node curr, List<Integer> result, int currDepth){

        if(curr == null){

            return;

        }

        if(currDepth == result.size()){

            result.add(curr.data);

        }

        

        leftView(curr.left, result, currDepth + 1);

        leftView(curr.right, result, currDepth + 1);

    }


    // Check if bianry tree is symmetric or not

    static boolean isSymmetricUtil(Node  root1, Node  root2) {

        if (root1 == null || root2 == null)

          return root1 == root2;

        return (root1 . data == root2 . data) && isSymmetricUtil(root1 . left, root2 . 

        right) && isSymmetricUtil(root1 . right, root2 . left);

      }

      static boolean isSymmetric(Node  root) {

        if (root==null) return true;

        return isSymmetricUtil(root . left, root . right);

      }

      

      // Print root to node path

      static boolean getPath(Node root, ArrayList < Integer > arr, int x) {

         

        if (root == null)

            return false;

        arr.add(root.data);

        if (root.data == x)

            return true;

        if (getPath(root.left, arr, x) ||

            getPath(root.right, arr, x))

            return true;

        arr.remove(arr.size() - 1);

        return false;

    }


    public static void  printPath(Node root, int node_data)

    {

        ArrayList < Integer > arr = new ArrayList < > ();

        boolean res;

        res = getPath(root, arr, node_data);


        System.out.print("The Root to node path is: ");

        for (int it: arr) {

            System.out.print(it + " ");

        }

    }


    // lowest common ancestor of binary tree

     public static Node lowestCommonAncestor(Node root, Node p, Node q) {

        if (root == null || root == p || root == q) {

            return root;

        }

        Node left = lowestCommonAncestor(root.left, p, q);

        Node right = lowestCommonAncestor(root.right, p, q);


        //result

        if(left == null) {

            return right;

        }

        else if(right == null) {

            return left;

        }

        else { //both left and right are not null, we found our result

            return root;

        }

    }


    // Maximum width of a binary tree

    public static int widthOfBinaryTree(Node root) {

        if(root == null) return 0;

        int ans = 0;

        Queue<Pair> q = new LinkedList<>(); 

        q.offer(new Pair(root, 0)); 

        while(!q.isEmpty()){

            int size = q.size();

            int mmin = q.peek().hd;    //to make the id starting from zero  

            int first = 0,last = 0;   //hd code written in Pair class

            for(int i=0; i<size; i++){

                int cur_id = q.peek().hd-mmin;

                Node node = q.peek().node;

                q.poll();

                if(i==0) first = cur_id;

                if(i==size-1) last = cur_id;

                if(node.left != null)

                    q.offer(new Pair(node.left, cur_id*2+1));

                if(node.right != null) 

                    q.offer(new Pair(node.right, cur_id*2+2));

            }

            ans = Math.max(ans, last-first+1);

        }

        return ans;

    }


 

    public static void main(String[] args) {

        Scanner scanner = new Scanner(System.in);

        BinaryTree bt = new BinaryTree();

        

        System.out.print("Enter root node value: ");

        int rootValue = scanner.nextInt();

        Node root = new Node(rootValue);


        root.left = bt.buildTree(scanner, "left", rootValue);

        root.right = bt.buildTree(scanner, "right", rootValue);


        System.out.println("Tree construction complete.");

        levelorder(root);

        System.out.println(preorderUsingStack(root));

        System.out.println(inorderUsingStack(root));

        System.out.println(postorderUsing2Stack(root));

        System.out.println(postorderUsing1Stack(root));

        ArrayList<Integer> preorderArrayList = new ArrayList<Integer>();

        ArrayList<Integer> inorderArrayList = new ArrayList<Integer>();

        ArrayList<Integer> postorderArrayList = new ArrayList<Integer>();

        preInPost_traversal_in_one(root, preorderArrayList, inorderArrayList, postorderArrayList);

        System.out.print("The preorder traversal is: ");

        for (Integer pre : preorderArrayList) {

            System.out.print(pre+" ");

        }

        System.out.println();

        System.out.print("The inorder traversal is: ");

        for (Integer in : inorderArrayList) {

            System.out.print(in+" ");

        }

        System.out.println();

        System.out.print("The postorder traversal is: ");

        for (Integer post : postorderArrayList) {

            System.out.print(post+" ");

        }

        System.out.println();

        System.out.println("The depth of your tree is: "+maxDepthOfBinaryTree(root));

        boolean balanced_var = isBalancedBinaryTree_boolean_value(root);

        System.out.println(balanced_var);

        System.out.println("The diameter of given binary tree is: "+diameterofbinarytree(root));

        System.out.println("The maximum path sum is: "+maxPathSum(root));

        System.out.println("The zigZag Traversal is: "+zigZagTraversal(root));

        System.out.println("The boundary traversal is as below:");

        boundaryTraversal(root);

        System.out.println();

        System.out.println("The vertical order traversal is as below:");

        TreeMap<Integer, Vector<Integer>> m = new TreeMap<>();

        int hd = 0;

        verticalOrder(root, hd, m);

        for (Map.Entry<Integer,Vector<Integer>> e : m.entrySet()) {

            System.out.println(e.getValue());

        }

        System.out.println("Top view traversal is :");

        System.out.println(topView(root));

        System.out.println("Bottom view traversal is :");

        System.out.println(bottomView(root));

        System.out.println("The right-side view is:");

        System.out.println(rightSideView(root));

        System.out.println("The left-side view is:");

        System.out.println(leftSideView(root));

        System.out.println("The binary tree is symmetric: "+isSymmetric(root));

        printPath(root, 7);

        System.out.println();

        //System.out.println("The lowest common ancestor is: "+lowestCommonAncestor(root, root.left.left, root.left.right.right).data);

        System.out.println("The maximum width of a binary tree is: "+widthOfBinaryTree(root));

        scanner.close();

    }

}



  

No comments:

Post a Comment

Good thoughtful question on Binary search on answers

Problem link:  https://leetcode.com/problems/maximize-score-of-numbers-in-ranges/description/ Solution: //import java.util.Arrays; class So...