Ocean FlowLoading saved progress…

Ocean Flow

Rain falls on an island of square cells, each with a height. Water runs from a cell into any directly adjacent cell whose height is equal to or lower than its own, and keeps running until it reaches an ocean. The Pacific laps the island's top and left edges; the Atlantic laps the bottom and right edges. You implement oceanFlow(heights), returning every cell from which water can drain to both oceans. This is the classic Pacific Atlantic Water Flow problem.

Signature

// heights: number[][]
//   An m x n grid. heights[r][c] is the height of the cell at row r, column c.
// returns: Array<[number, number]>
//   Every [row, col] from which water can reach BOTH oceans.
//   Returned in row-major order (see Notes).
function oceanFlow(heights): Array<[number, number]>;

Examples

// The classic 5x5 grid.
oceanFlow([
  [1, 2, 2, 3, 5],
  [3, 2, 3, 4, 4],
  [2, 4, 5, 3, 1],
  [6, 7, 1, 4, 5],
  [5, 1, 1, 2, 4],
]);
// → [[0,4],[1,3],[1,4],[2,2],[3,0],[3,1],[4,0]]
// A single cell touches all four edges, so it reaches both oceans.
oceanFlow([[42]]); // → [[0, 0]]
// A deep pit: the center cell (height 1) is walled in by 10s. Water there
// cannot climb out to any edge, so it reaches NEITHER ocean and is excluded.
oceanFlow([
  [10, 10, 10],
  [10,  1, 10],
  [10, 10, 10],
]);
// → every border cell, but NOT [1, 1]

Notes

  • Flow is 4-directional. Water moves up, down, left, or right — never diagonally.
  • Equal-or-lower flow. Water flows from a cell to a neighbour whose height is <= the current cell's height. Equal heights count: water can move freely between two cells of the same height.
  • Pacific = top + left edges; Atlantic = bottom + right edges. Any cell on the top row or left column already touches the Pacific; any cell on the bottom row or right column already touches the Atlantic.
  • Output ordering is row-major. Scan rows top-to-bottom, and within each row scan columns left-to-right. So [0, 4] precedes [1, 3], which precedes [2, 2]. If you prefer to compare results as an unordered set, sort both sides first.
  • Empty input returns []. An empty grid ([]) or a grid of empty rows ([[]]) yields an empty list.
  • Don't worry about ties producing different valid orderings (we pin one), 8-directional flow, or grids large enough to overflow the recursion stack — recursion is fine for the sizes here.
Loading editor…