Talentd
FleetCode
Make and follow sheets.Sign in

Maximum Binary Tree II solution and explanation

MediumBinary TreeTree7 min read70.8% acceptanceUpdated 9 Apr 2026
998. Maximum Binary Tree IIMuerde un zombie · 3:30 · 364 viewsWatch on YouTube
9 more videos on this problem
  1. 998. Maximum Binary Tree IIMuerde un zombie · 3:30 · 364 views
  2. Leetcode 998AUM · 33:42 · 264 views
  3. 998. Maximum Binary Tree II (Leetcode Medium)Programming Live with Larry · 9:12 · 248 views
  4. leetcode 998. Maximum Binary Tree II - recursionCode-Yao · 13:16 · 231 views
  5. 猩猩的乐园 Leetcode 998 Maximum Binary Tree II猩猩的乐园 · 5:42 · 196 views
  6. Leetcode | Java | 998. Maximum Binary Tree II | Programming FizzBuzz challengeIvan Kopylov · 14:23 · 94 views
  7. Maximum Binary Tree II, Medium, LeetCode 998H William Polenz · 18:30 · 70 views
  8. Leetcode 998. Maximum Binary Tree II (create tree)LetsCode · 9:16 · 46 views
  9. No Sound Leetcode 998: Maximum Binary Tree IIExtremeProgrammer · 0:49 · 27 views
  10. Maximum Binary Tree II #leetcode #programming short #java #BinaryTreecoding_kida · 0:11 · 18 views

The problem

A maximum tree is a tree where every node has a value greater than any other value in its subtree.

You are given the root of a maximum binary tree and an integer val.

Just as in the previous problem, the given tree was constructed from a list a (root = Construct(a)) recursively with the following Construct(a) routine:

  • If a is empty, return null.
  • Otherwise, let a[i] be the largest element of a. Create a root node with the value a[i].
  • The left child of root will be Construct([a[0], a[1], ..., a[i - 1]]).
  • The right child of root will be Construct([a[i + 1], a[i + 2], ..., a[a.length - 1]]).
  • Return root.

Note that we were not given a directly, only a root node root = Construct(a).

Suppose b is a copy of a with the value val appended to it. It is guaranteed that b has unique values.

Return Construct(b).

Example 1:

Input: root = [4,1,3,null,null,2], val = 5
Output: [5,4,null,1,3,null,null,2]
Explanation: a = [1,4,2,3], b = [1,4,2,3,5]

Example 2:

Input: root = [5,2,4,null,1], val = 3
Output: [5,2,4,null,1,null,3]
Explanation: a = [2,1,5,4], b = [2,1,5,4,3]

Example 3:

Input: root = [5,2,3,null,1], val = 4
Output: [5,2,4,null,1,3]
Explanation: a = [2,1,5,3], b = [2,1,5,3,4]

Constraints:

  • The number of nodes in the tree is in the range [1, 100].
  • 1 <= Node.val <= 100
  • All the values of the tree are unique.
  • 1 <= val <= 100

Approach overview

Problem Overview: You are given the root of a maximum binary tree built from an array and a new value val appended to that array. The task is to update the tree so it represents the maximum binary tree of the new array after the insertion.

A maximum binary tree has two rules: the root is the maximum value in the array, and the left and right subtrees are built recursively from the elements on each side of that maximum. When a new value is appended, it can only affect nodes along the rightmost path of the tree.

Approach 1: Recursive Tree Modification (O(n) time, O(h) space)

This method directly simulates how the tree would change if the new value were appended to the array. Compare val with the current node. If val is greater than the current root, the new value becomes the new root and the previous tree becomes its left child. Otherwise, the insertion must occur somewhere in the right subtree because the value was appended to the end of the array. Recursively process root.right until the correct position is found. The recursion depth equals the tree height h, giving O(n) worst-case time and O(h) space due to the call stack. This approach is clean and closely matches the recursive definition of a tree.

Approach 2: Iterative Approach using Stack (O(n) time, O(n) space)

The iterative solution leverages a monotonic structure similar to how the original maximum binary tree can be built. Traverse the right spine of the tree using a stack to track nodes. While the stack top has a value smaller than val, pop nodes because the new value must become their parent. The last popped node becomes the left child of the new node. If a larger node remains on the stack, attach the new node as its right child. This approach avoids recursion and works well when you want explicit control over traversal. Time complexity is O(n) since each node is pushed and popped at most once, and auxiliary space is O(n). The logic relies on properties of binary tree structure and a monotonic stack.

Recommended for interviews: The recursive modification approach is typically expected because it directly uses the definition of a maximum binary tree and quickly leads to a clean solution. Interviewers often look for the key observation that the insertion only affects the rightmost path. The iterative stack version demonstrates deeper understanding of tree construction patterns and monotonic stacks, which can stand out in more advanced interviews.

Approach 1: Recursive Tree Modification

This approach involves recursively inserting the new value into the correct position in the maximum binary tree. The main idea is to find the correct place in the tree for the new value by comparing it with the current node values as we traverse the tree from top to bottom.

If the new value is greater than the root node, the new value becomes the new root, and the entire existing tree becomes its left subtree. Otherwise, recursively consider this insertion as a problem for the root's right subtree, as all existing left-side nodes are already smaller than the current root.

class TreeNode:
    def __init__(self, val=0, left=None, right=None):
        self.val = val
        self.left = left
        self.right = right

def insertIntoMaxTree(root, val):
    if not root or val > root.val:
        return TreeNode(val, left=root)
    root.right = insertIntoMaxTree(root.right, val)
    return root
struct TreeNode {
    int val;
    TreeNode *left;
    TreeNode *right;
    TreeNode(int x) : val(x), left(NULL), right(NULL) {}
};

TreeNode* insertIntoMaxTree(TreeNode* root, int val) {
    if (!root || val > root->val)
        return new TreeNode(val, root);
    root->right = insertIntoMaxTree(root->right, val);
    return root;
}

We define a TreeNode class to represent each node in the tree. The insertIntoMaxTree function accepts the root of the tree and an integer val. If the root is null (empty tree) or the val is greater than the root's value, we make val the new root node with the current root as its left child. Otherwise, we recursively try to insert val into the right subtree.

Complexity

Time Complexity: O(n), where n is the number of nodes in the tree.
Space Complexity: O(n) in the worst case due to the recursion stack.

Try this approach in the editor

Approach 2: Iterative Approach using Stack

This approach attempts to solve the problem using an iterative method with the help of a stack to simulate the recursive behavior. As the new value is only appended to the right-most part of the implied array, we have to check from right to left in the tree structure to find the appropriate place for the new value to maintain the maximum tree property.

The main idea is to traverse the right nodes of the tree using a stack until we find the correct position for the new node.

class TreeNode {
    int val;
    TreeNode left, right;
    TreeNode(int val) { this.val = val; }
}

public TreeNode insertIntoMaxTree(TreeNode root, int val) {
    TreeNode node = new TreeNode(val);
    if (root == null || val > root.val) {
        node.left = root;
        return node;
    }
    TreeNode current = root;
    while (current.right != null && current.right.val > val) {
        current = current.right;
    }
    node.left = current.right;
    current.right = node;
    return root;
}
function TreeNode(val, left = null, right = null) {
    this.val = val;
    this.left = left;
    this.right = right;
}

function insertIntoMaxTree(root, val) {
    let node = new TreeNode(val);
    if (root === null || val > root.val) {
        node.left = root;
        return node;
    }
    let cur = root;
    while (cur.right !== null && cur.right.val > val) {
        cur = cur.right;
    }
    node.left = cur.right;
    cur.right = node;
    return root;
}

This solution uses a loop instead of a recursive approach to insert the node. We iterate down the chain of right children until we find a spot where the new node should be inserted. This will involve attaching the new node's left subtree as the right child of the current node.

Complexity

Time Complexity: O(n), where n is the number of nodes in the tree.
Space Complexity: O(1) since additional structures (e.g., a stack) are not used.

Try this approach in the editor

Approach 3: Recursion

If val is the maximum number, then make val the new root node, and root the left subtree of the new root node.

If val is not the maximum number, since val is the last appended number, it must be on the right side of root. Therefore, we can insert val as a new node into the right subtree of root.

The time complexity is O(n), and the space complexity is O(n). Here, n is the number of nodes in the tree.

/**
 * Definition for a binary tree node.
 * class TreeNode {
 *     val: number
 *     left: TreeNode | null
 *     right: TreeNode | null
 *     constructor(val?: number, left?: TreeNode | null, right?: TreeNode | null) {
 *         this.val = (val===undefined ? 0 : val)
 *         this.left = (left===undefined ? null : left)
 *         this.right = (right===undefined ? null : right)
 *     }
 * }
 */

function insertIntoMaxTree(root: TreeNode | null, val: number): TreeNode | null {
    if (!root || root.val < val) {
        return new TreeNode(val, root);
    }
    root.right = insertIntoMaxTree(root.right, val);
    return root;
}
/**
 * Definition for a binary tree node.
 * struct TreeNode {
 *     int val;
 *     struct TreeNode *left;
 *     struct TreeNode *right;
 * };
 */

struct TreeNode* insertIntoMaxTree(struct TreeNode* root, int val) {
    if (!root || root->val < val) {
        struct TreeNode* res = (struct TreeNode*) malloc(sizeof(struct TreeNode));
        res->val = val;
        res->left = root;
        res->right = NULL;
        return res;
    }
    root->right = insertIntoMaxTree(root->right, val);
    return root;
}
/**
 * Definition for a binary tree node.
 * type TreeNode struct {
 *     Val int
 *     Left *TreeNode
 *     Right *TreeNode
 * }
 */
func insertIntoMaxTree(root *TreeNode, val int) *TreeNode {
	if root == nil || root.Val < val {
		return &TreeNode{val, root, nil}
	}
	root.Right = insertIntoMaxTree(root.Right, val)
	return root
}
// Definition for a binary tree node.
// #[derive(Debug, PartialEq, Eq)]
// pub struct TreeNode {
//   pub val: i32,
//   pub left: Option<Rc<RefCell<TreeNode>>>,
//   pub right: Option<Rc<RefCell<TreeNode>>>,
// }
//
// impl TreeNode {
//   #[inline]
//   pub fn new(val: i32) -> Self {
//     TreeNode {
//       val,
//       left: None,
//       right: None
//     }
//   }
// }
use std::cell::RefCell;
use std::rc::Rc;
impl Solution {
    pub fn insert_into_max_tree(
        mut root: Option<Rc<RefCell<TreeNode>>>,
        val: i32,
    ) -> Option<Rc<RefCell<TreeNode>>> {
        if root.is_none() || root.as_ref().unwrap().as_ref().borrow().val < val {
            return Some(Rc::new(RefCell::new(TreeNode {
                val,
                left: root.take(),
                right: None,
            })));
        }
        {
            let mut root = root.as_ref().unwrap().as_ref().borrow_mut();
            root.right = Self::insert_into_max_tree(root.right.take(), val);
        }
        root
    }
}
Try this approach in the editor

Approach 4: Iteration

Search the right subtree, find the node where curr.val \gt val \gt curr.right.val, then create a new node node, point node.left to curr.right, and then point curr.right to node.

Finally, return root.

The time complexity is O(n), where n is the number of nodes in the tree. The space complexity is O(1).

/**
 * Definition for a binary tree node.
 * class TreeNode {
 *     val: number
 *     left: TreeNode | null
 *     right: TreeNode | null
 *     constructor(val?: number, left?: TreeNode | null, right?: TreeNode | null) {
 *         this.val = (val===undefined ? 0 : val)
 *         this.left = (left===undefined ? null : left)
 *         this.right = (right===undefined ? null : right)
 *     }
 * }
 */

function insertIntoMaxTree(root: TreeNode | null, val: number): TreeNode | null {
    if (root.val < val) {
        return new TreeNode(val, root);
    }
    const node = new TreeNode(val);
    let curr = root;
    while (curr.right && curr.right.val > val) {
        curr = curr.right;
    }
    node.left = curr.right;
    curr.right = node;
    return root;
}
/**
 * Definition for a binary tree node.
 * type TreeNode struct {
 *     Val int
 *     Left *TreeNode
 *     Right *TreeNode
 * }
 */
func insertIntoMaxTree(root *TreeNode, val int) *TreeNode {
	if root.Val < val {
		return &TreeNode{val, root, nil}
	}
	node := &TreeNode{Val: val}
	curr := root
	for curr.Right != nil && curr.Right.Val > val {
		curr = curr.Right
	}
	node.Left = curr.Right
	curr.Right = node
	return root
}
Try this approach in the editor

Complexity comparison

ApproachComplexity
Recursive Tree Modification

Time Complexity: O(n), where n is the number of nodes in the tree.
Space Complexity: O(n) in the worst case due to the recursion stack.

Iterative Approach using Stack

Time Complexity: O(n), where n is the number of nodes in the tree.
Space Complexity: O(1) since additional structures (e.g., a stack) are not used.

Recursion–
Iteration–

Complexity analysis

ApproachTimeSpaceWhen to Use
Recursive Tree ModificationO(n)O(h)Best general solution. Clean logic and closely follows the definition of a maximum binary tree.
Iterative Stack ApproachO(n)O(n)Useful when avoiding recursion or when applying monotonic stack patterns.

Frequently asked questions

Is Maximum Binary Tree II easy or hard?

Maximum Binary Tree II is classified as a Medium problem. The main difficulty is recognizing that the new value only affects the rightmost path of the tree. Once that insight is clear, the recursive insertion logic becomes straightforward.

Maximum Binary Tree II Python/Java solution

Python and C++ solutions commonly use recursion to update the right subtree until the correct insertion point is found. Java and JavaScript implementations often demonstrate the iterative stack method to avoid recursion while preserving the maximum tree property.

How to solve Maximum Binary Tree II in O(n)?

Traverse only the right side of the tree since the inserted value corresponds to an element appended to the array. Compare the new value with nodes along the right path until a larger node is found or the end is reached. Insert the new node and reconnect children accordingly. Each node is visited at most once, giving O(n) time.

What is the best approach for Maximum Binary Tree II?

The recursive tree modification approach is the most common solution. Compare the new value with the current root and recurse only into the right subtree when the value is smaller. If the new value is larger, create a new root and attach the existing tree as its left child. This runs in O(n) worst-case time with O(h) recursion space.

Is Maximum Binary Tree II asked at Google/Amazon/Meta?

Tree modification and construction problems similar to Maximum Binary Tree II appear in interviews at companies like Amazon, Google, and Meta. Interviewers often use them to test understanding of tree properties, recursion, and structural transformations.

What data structure is used in Maximum Binary Tree II?

The core data structure is a binary tree. Some implementations also use a stack to manage nodes along the right spine and maintain a monotonic order while inserting the new value.

What is the time complexity of Maximum Binary Tree II?

Time complexity is O(n) in the worst case because the algorithm may traverse the entire right spine of the tree. In balanced trees the average complexity is closer to O(log n). Space complexity is O(h) for recursion, where h is the height of the tree.

Comments

Now write it yourselfClose this page and solve Maximum Binary Tree II in the editor, without looking.
Practise Maximum Binary Tree II