InterviewPrepKit

Home / Coding / Two Pointers

Trapping Rain Water

hard Original β†—
Solving tips
  • Start from the per-cell formula: water[i] = min(maxLeft[i], maxRight[i]) - height[i], clamped at 0; everything else is how to compute those maxima efficiently.
  • The clean O(n)/O(n) baseline is prefix and suffix max arrays; state it before optimizing to the O(1)-space two-pointer version.
  • For O(1) space, walk both ends carrying running left_max and right_max, and always advance the side with the smaller bar since its running max is the binding min and the unseen side can only be taller.
  • Pitfall: process the smaller side, not the larger; a monotonic stack (O(n) space) is the other O(n) option and needs careful width = i - left_wall - 1 and depth off the popped floor.

Problem

You are given an array height where height[i] is the height of a bar of width 1 standing at position i, forming an elevation profile. After it rains, water settles in the valleys between taller bars. Return the total number of unit squares of water the profile traps.

Water above position i rises to the level of the shorter of the tallest bar to its left and the tallest bar to its right β€” anything higher spills off the ends.

Examples

Example 1

Input:  height = [0, 1, 0, 2, 1, 0, 1, 3, 2, 1, 2, 1]
Output: 6

One unit sits at index 2, one at index 4, two at index 5, one at index 6, one at index 9.

Example 2

Input:  height = [4, 2, 0, 3, 2, 5]
Output: 9

The walls of height 4 and 5 trap 2 + 4 + 1 + 2 = 9 units over indices 1–4.

Example 3

Input:  height = [3, 1, 2]
Output: 1

Index 1 holds water up to min(3, 2) = 2, i.e. 1 unit. Monotonic profiles trap nothing.

Constraints

  • 1 <= height.length <= 2 * 10^4
  • 0 <= height[i] <= 10^5
  • An O(n^2) rescan per position is too slow; O(n) is expected, and O(1) space is the flourish.

Think about it first

Hint 1 Water above a single position depends on exactly two quantities. Write the formula for the water at index `i` before thinking about any algorithm.
Hint 2 `water[i] = min(max_left[i], max_right[i]) - height[i]` (clamped at 0). Both max-arrays can be precomputed in one sweep each. That's already O(n) β€” now try to drop the arrays.
Hint 3 Walk pointers in from both ends carrying running maxima. When `left_max < right_max`, the water level at the left pointer is decided by `left_max` alone β€” some wall of at least `right_max β‰₯ left_max` exists to the right, so the true right max can only be bigger and the min is already known. Settle that cell and move inward.
Your workspace Not runnable by design β€” this is your interview scratchpad. Saved on this device.