Maximum Nesting Depth of the Parentheses: Counter Pattern
Maximum Nesting Depth of the Parentheses is LeetCode problem 1614, rated Easy. You are given a valid parentheses string (VPS) s that contains digits, +, *, /, -, and parentheses. Your job is to return the maximum nesting depth of the parentheses. For example, "(1+(2*3)+((8)/4))+1" has a nesting depth of 3.
Why this problem matters
This problem looks almost too simple, and that is exactly what makes it valuable. It teaches you that many problems which seem like they need a stack can actually be solved with a single integer counter. You will see this counter pattern again in problems like checking for balanced parentheses, tracking recursion depth, and evaluating nested expressions. Learning to spot when a counter replaces a stack is a skill that transfers to dozens of problems.
It also reinforces the idea of scanning left to right and maintaining state as you go. That one-pass, constant-space mindset is one of the most useful patterns in string processing.
The key insight
A stack-based solution would push on every ( and pop on every ). But you never actually need the stack contents. You only care about the stack's size. Since each ( increases the size by one and each ) decreases it by one, you can replace the entire stack with a single integer counter. Increment on (, decrement on ), and track the maximum value the counter ever reaches.
That maximum value is the answer.
The solution
def maxDepth(s: str) -> int:
depth = 0
max_depth = 0
for ch in s:
if ch == '(':
depth += 1
if depth > max_depth:
max_depth = depth
elif ch == ')':
depth -= 1
return max_depth
The code walks through the string one character at a time. Every opening parenthesis increases depth by one, and we check if this new depth exceeds our running max_depth. Every closing parenthesis decreases depth by one. Characters that are not parentheses are simply ignored.
Because the input is guaranteed to be a valid parentheses string, you never need to worry about depth going negative or having unmatched brackets. The problem statement guarantees well-formed input.
Updating max_depth only on the ( branch is enough. The depth peaks right after an open paren, never after a close paren. This saves one comparison per closing bracket.
Visual walkthrough
Let's trace through "(1+(2*3)+((8)/4))+1" step by step, watching the depth counter rise and fall as we hit each parenthesis.
Step 1: Read '(' at index 0. Open paren, depth goes from 0 to 1.
First opening paren. current = 1, max = 1.
Step 2: Read '(' at index 3. Open paren, depth goes from 1 to 2.
Nested inside the first paren. current = 2, max = 2.
Step 3: Read ')' at index 7. Close paren, depth goes from 2 to 1.
The inner group (2*3) is closed. current = 1, max stays 2.
Step 4: Read '(' at index 9. Then '(' at index 10. Depth jumps from 1 to 2 to 3.
Two consecutive opens. current = 3, max = 3. This is the deepest point.
Step 5: Read ')' at index 12, ')' at index 15, ')' at index 16. Depth drops from 3 to 0.
All parens closed. current = 0, max = 3. The answer is 3.
Complexity analysis
| Approach | Time | Space |
|---|---|---|
| Counter (optimal) | O(n) | O(1) |
| Stack-based | O(n) | O(n) |
The counter approach is strictly better on space. Both approaches scan the string once, so time is identical. Since you never need to know which parenthesis is on the stack, only how many, the counter wins.
The building blocks
1. Counter instead of stack
When a stack is used only for tracking depth (not for storing actual values you need later), replace it with an integer. Increment on push, decrement on pop. This converts O(n) space to O(1) space while preserving all the information you need. You will see this same trick in problems that count nesting levels, track recursion depth, or validate simple bracket strings.
2. One-pass max tracking
Maintaining a running maximum as you scan is a fundamental pattern. Instead of computing all values first and then finding the max, you update max_depth on the fly. This works whenever the quantity you are maximizing can be computed incrementally. The same approach shows up in maximum subarray, best time to buy/sell stock, and many other problems.
Edge cases
- No parentheses at all. A string like
"1+2"has no parentheses, sodepthnever changes andmax_depthstays 0. That is the correct answer. - Single pair.
"(1)"reaches depth 1 and returns 1. - Flat sequence.
"(1)+(2)+(3)"reaches depth 1 three times but never goes deeper. The answer is 1, not 3. - Deeply nested.
"((((1))))"reaches depth 4. The counter handles this with no extra memory regardless of how deep the nesting goes. - Mixed content. The string can contain
+,-,*,/, and digits. The algorithm simply ignores all non-parenthesis characters.
From understanding to recall
Maximum Nesting Depth feels trivial once you see the counter trick. Increment on (, decrement on ), track the max. Five lines of code. But the real value is recognizing when this trick applies. In an interview, you might get a problem that looks like it needs a stack, and spotting that a counter is sufficient could be the difference between an O(n) space solution and an O(1) space solution.
The way to lock this in is practice. Not re-reading the solution, but reconstructing it from scratch. Spaced repetition forces you to recall the pattern at increasing intervals until it becomes automatic. After a few rounds, you will not just remember this specific problem. You will recognize the counter-replaces-stack pattern every time it appears.
Related posts
- Valid Parentheses - Stack-based parentheses validation
- Generate Parentheses - Generating valid parentheses
- Longest Valid Parentheses - Finding longest valid parentheses substring
Maximum Nesting Depth is a small problem with a big lesson. Stacks are powerful, but when all you need is a count, a single integer does the job.