{x}
blog image

Maximum Product of Splitted Binary Tree

Given the root of a binary tree, split the binary tree into two subtrees by removing one edge such that the product of the sums of the subtrees is maximized.

Return the maximum product of the sums of the two subtrees. Since the answer may be too large, return it modulo 109 + 7.

Note that you need to maximize the answer before taking the mod and not after taking it.

 

Example 1:

Input: root = [1,2,3,4,5,6]
Output: 110
Explanation: Remove the red edge and get 2 binary trees with sum 11 and 10. Their product is 110 (11*10)

Example 2:

Input: root = [1,null,2,3,4,null,null,5,6]
Output: 90
Explanation: Remove the red edge and get 2 binary trees with sum 15 and 6.Their product is 90 (15*6)

 

Constraints:

  • The number of nodes in the tree is in the range [2, 5 * 104].
  • 1 <= Node.val <= 104

Solution Explanation

This problem asks to find the maximum product of the sums of two subtrees obtained by removing one edge from a binary tree. The solution uses a depth-first search (DFS) approach combined with a pre-calculation of the total sum of the tree's nodes.

Algorithm:

  1. Calculate the total sum: A helper function sum(root) recursively calculates the sum of all node values in the tree. This sum represents the total sum of all nodes, which will be used later to compute the sum of the second subtree after an edge is removed.

  2. Depth-First Search (DFS): The core logic is implemented in the dfs(root) function. This function recursively traverses the tree:

    • For each node, it calculates the sum of the subtree rooted at that node.
    • It compares this subtree sum (t) with the total sum (s) calculated in step 1. If the subtree sum is less than the total sum, it means removing the edge connecting this node to its parent would result in two valid subtrees. It then updates the maximum product (ans) by considering the product of the subtree sum (t) and the remaining sum (s - t).
    • It returns the subtree sum (t) to its parent node for further calculations.
  3. Modulo Operation: Finally, the result is taken modulo 10^9 + 7 to handle potential integer overflow, and the maximum product ans is returned.

Time Complexity Analysis:

The sum() function and the dfs() function both perform a single traversal of the tree. Therefore, the time complexity is O(N), where N is the number of nodes in the tree.

Space Complexity Analysis:

The space complexity is determined by the recursive call stack of dfs(), which in the worst-case scenario (a skewed tree) can be O(N) in height. In the average case (balanced tree), the space complexity will be O(log N).

Code Explanation (Python):

class Solution:
    def maxProduct(self, root: Optional[TreeNode]) -> int:
        def sum(root: Optional[TreeNode]) -> int:
            if root is None:
                return 0
            return root.val + sum(root.left) + sum(root.right)
 
        def dfs(root: Optional[TreeNode]) -> int:
            if root is None:
                return 0
            t = root.val + dfs(root.left) + dfs(root.right)
            nonlocal ans, s
            if t < s:
                ans = max(ans, t * (s - t))
            return t
 
        mod = 10**9 + 7
        s = sum(root)
        ans = 0
        dfs(root)
        return ans % mod

The Python code directly implements the algorithm as described above. The nonlocal keyword is crucial because ans and s are modified within the nested function dfs(). Other languages handle this differently (e.g., using class members in Java). The rest of the code is a straightforward translation of the algorithm into the respective programming language. The modulo operation at the end ensures that the result remains within the specified range.