GeeksforGeeks Medium

Next Smaller Element

For each element, find the first smaller element to its right (−1 if none).

stackmonotonic-stack
Open on GeeksforGeeks ↗
02

Intuition

Next Greater with the comparison flipped: keep an increasing stack of waiters; each new element pops — answers — every waiter larger than it.

How to spot this pattern

Identical machinery to next-greater with the comparison flipped, which also flips what the stack holds: values now sit in increasing order. Seeing that one operator controls the stack's whole invariant is the transferable part — it's how you'd derive previous-smaller or previous-greater on the spot.

03

Approach

1

Mirror the monotonic stack

Stack holds indices with increasing values. New value x pops all waiters > x; x is their next smaller.

2

Drain leftovers as −1

Anything still waiting at the end has no smaller element to its right.

3

Same amortized bound

Push+pop once per index → O(n).

04

Solution & live demo

1def next_smaller(nums):
2 res = [-1] * len(nums)
3 stack = [] # indices, values increasing
4 for i, x in enumerate(nums):
5 while stack and nums[stack[-1]] > x:
6 res[stack.pop()] = x
7 stack.append(i)
8 return res
05

Common pitfalls

Flipping the comparison but expecting a decreasing stack

✗ Wrong
stack = []   # indices, values decreasing
while stack and nums[stack[-1]] > x:
✓ Right
stack = []   # indices, values increasing
while stack and nums[stack[-1]] > x:

The code is right; the mental model isn't. Popping everything larger than the newcomer leaves the stack increasing from bottom to top. Carrying over next-greater's "decreasing" assumption is what makes the follow-up variants go wrong.

Using >= and mis-answering equal values

✗ Wrong
while stack and nums[stack[-1]] >= x:
✓ Right
while stack and nums[stack[-1]] > x:

An equal element is not smaller, so resolving a pending index with it reports a wrong answer — on [2, 2] the first index would get 2 instead of -1. Strictness in the pop test must match strictness in the question.

06

Edge cases

Increasing array

No pops until the end — all −1? No: each element's right neighbours are larger, so yes, all −1.

Equal neighbours

Strictly-smaller wanted → equals stay on the stack.

07

Complexity

Time
O(n)
Space
O(n)
Monotonic stack, one pass.