Convert BST to Greater Sum Tree asks you to rewrite every node so it holds the sum of all values greater than or equal to it. The clean solution exploits the one thing a BST gives you for free: an ordering. A small twist on in-order traversal turns this into a single elegant pass.
Problem. Given the root of a binary search tree, replace each node's value with the sum of all values in the tree that are greater than or equal to that node's value. Return the modified tree.
Example: the BST with values 1, 2, 4, 5, 6, 7 becomes 25, 24, 22, 18, 13, 7 — node 7 stays 7
(nothing is larger), node 6 becomes 6 + 7 = 13, and node 1 becomes the sum of everything, 25.
The slow way first
The obvious idea: for each node, scan the entire tree and add up every value that is greater than or equal to it. That is O(n²) — a full traversal per node. We can do far better by noticing that a BST already stores its values in sorted order, so we never need to re-scan.
The question to ask: for a given node, which values are greater than it? In a BST, the answer is "everything to its right" — and an in-order walk visits values in ascending order. So if we walk in the reverse direction, we meet values from largest to smallest, and a single running total is all the bookkeeping we need.
The idea: reverse in-order with a running total
A normal in-order traversal goes left → node → right and yields values in increasing order. Flip it to right → node → left and you get values in decreasing order. Keep a total that we add each node's value to as we visit it; because we visit larger values first, total is always the sum of everything we have already seen — which is exactly the set of values greater than the current node. Assign total back into the node.
The key insight: by the time we reach a node, every value greater than it has already been folded into total, so one assignment is correct and final.
Walk through it
Step through the animation. We dive right to the largest value 7 and set total = 7. Backing out, 6 becomes 7 + 6 = 13, then its left child 5 becomes 18. We return to the root 4 for 22, then descend left to handle 2 (24) and finally 1 (25). One pass, smallest written last.
Pseudocode
total = 0
visit(node):
if node is null: return
visit(node.right) # larger values first
total = total + node.val # fold this node into the running sum
node.val = total # this node = sum of all values >= it
visit(node.left) # then the smaller values
visit(root)
return rootThe Python solution
def bst_to_gst(root):
total = 0
def visit(node):
nonlocal total
if node is None:
return
visit(node.right)
total += node.val
node.val = total
visit(node.left)
visit(root)
return roottotalis the running sum of every value visited so far — and since we go largest-first, that is every value greater than or equal to the current node.nonlocal totallets the innervisitmutate the accumulator defined in the outer function.visit(node.right)is the crucial reversal: we recurse right first so larger values are processed before the current node.total += node.valthennode.val = totalfolds the node in and writes back the answer.visit(node.left)handles the smaller values last.
Complexity
| Case | Time | Notes |
|---|---|---|
| Brute force (rescan per node) | O(n²) (slow) | a full traversal for every node |
| Reverse in-order (this solution) | O(n) (moderate) | one pass, each node visited once |
O(h) (moderate)The time drops from O(n²) to O(n) — we touch each node exactly once. The extra space is O(h) for the recursion stack, where h is the tree height (O(log n) for a balanced tree, O(n) in the worst case).
When this pattern shows up
Whenever a BST problem asks about values in sorted order — kth largest, range sums, successor, or "greater than" relationships — think in-order traversal, and remember it runs in reverse when you want largest-first. A single running accumulator often replaces an entire nested loop.
The direction matters: it must be right → node → left. A normal left-first traversal accumulates the smaller values first and gives each node the sum of values less than it — the opposite of what is asked.
Practice
In the example tree, by the time we visit the root 4, which values have already been added to total, and what does 4 become?
1. Why does a reverse in-order traversal solve this problem in one pass?
2. What order does a normal (left → node → right) in-order traversal produce on a BST?
3. What is the time complexity of the reverse in-order solution?
4. Why must we recurse into node.right before updating the current node?