150NeetCode 150

27.Largest Rectangle in Histogram

HardStack · 7/7

Problem

Given an array heights where heights[i] is the height of a histogram bar of width 1, return the area of the largest rectangle that fits entirely inside the histogram.

A rectangle spans a contiguous range of bars, and its height is limited by the shortest bar in that range.

Examples

Input:  heights = [2, 1, 5, 6, 2, 3]
Output: 10
Explanation: Bars 5 and 6 (indices 2–3) form a rectangle of height 5 and width 2 → area 10.
Input:  heights = [2, 4]
Output: 4
Explanation: Either the single bar of height 4, or both bars at height 2 — both give area 4.

Constraints

  • 1 <= heights.length <= 10^5
  • 0 <= heights[i] <= 10^4

💡 Key Insight

The best rectangle has some bar i as its shortest bar, and then it should extend as far as possible: left until the first shorter bar, right until the first shorter bar. Its area is heights[i] * (right - left - 1). A monotonic increasing stack finds both boundaries for every bar in a single pass: when bar i is popped by a shorter bar, that shorter bar is its right boundary and the new stack top is its left boundary.

Brute Force

TimeO(n²)SpaceO(1).

Intuition

Try every range [i, j]. Extending j one bar at a time, keep the running minimum height; the rectangle for that range has area minHeight * (j - i + 1).

Algorithm

  1. maxArea = 0.
  2. For each i: minHeight = +infinity.
  3. For each j >= i: minHeight = min(minHeight, heights[j]); maxArea = max(maxArea, minHeight * (j - i + 1)).
  4. Return maxArea.

Visualization

heights = [2, 1, 5, 6, 2, 3]

i=2: [5] → 5·1=5, [5,6] → 5·2=10 ✓, [5,6,2] → 2·3=6, [5,6,2,3] → 2·4=8
i=1: [1..] → min is 1 everywhere → at most 1·5=5
best = 10

Code

java
class Solution {
    public int largestRectangleArea(int[] heights) {
        int n = heights.length;
        int maxArea = 0;
        for (int i = 0; i < n; i++) {
            int minHeight = Integer.MAX_VALUE;
            for (int j = i; j < n; j++) {
                minHeight = Math.min(minHeight, heights[j]); // shortest bar in [i, j]
                maxArea = Math.max(maxArea, minHeight * (j - i + 1));
            }
        }
        return maxArea;
    }
}

Complexity

  • Time: O(n²) — every range is examined; too slow for n = 10^5.
  • Space: O(1).

Complexity Comparison

Approach Time Space
Brute Force O(n²) O(1)
Nearest Smaller (two passes) O(n) O(n)
One-Pass Monotonic Stack O(n) O(n)

Common Pitfalls

  • Computing the width as i - poppedIndex — the rectangle extends left past the popped index to just after the new stack top, so use i - stack.peek() - 1.
  • Forgetting to flush the stack at the end; an increasing histogram like [1, 2, 3] would never pop. The 0-height sentinel fixes this.
  • Mishandling the empty-stack case: when nothing shorter remains on the left, the rectangle starts at index 0, so the width is i.
  • Worrying about overflow: the max area is 10^4 * 10^5 = 10^9, which still fits in an int.