[LeetCode] 417. Pacific Atlantic Water Flow

There is an m x n rectangular island that borders both the Pacific Ocean and Atlantic Ocean. The Pacific Ocean touches the island's left and top edges, and the Atlantic Ocean touches the island's right and bottom edges.

The island is partitioned into a grid of square cells. You are given an m x n integer matrix heights where heights[r][c] represents the height above sea level of the cell at coordinate (r, c).

The island receives a lot of rain, and the rain water can flow to neighboring cells directly north, south, east, and west if the neighboring cell's height is less than or equal to the current cell's height. Water can flow from any cell adjacent to an ocean into the ocean.

Return a 2D list of grid coordinates result where result[i] = [ri, ci] denotes that rain water can flow from cell (ri, ci) to both the Pacific and Atlantic oceans.

Example 1:

Input: heights = [[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]]
Output: [[0,4],[1,3],[1,4],[2,2],[3,0],[3,1],[4,0]]

Example 2:

Input: heights = [[2,1],[1,2]]
Output: [[0,0],[0,1],[1,0],[1,1]]

Constraints:

  • m == heights.length
  • n == heights[r].length
  • 1 <= m, n <= 200
  • 0 <= heights[r][c] <= 105

太平洋大西洋水流问题。

有一个 m × n 的矩形岛屿,与 太平洋 和 大西洋 相邻。 “太平洋” 处于大陆的左边界和上边界,而 “大西洋” 处于大陆的右边界和下边界。

这个岛被分割成一个由若干方形单元格组成的网格。给定一个 m x n 的整数矩阵 heights , heights[r][c] 表示坐标 (r, c) 上单元格 高于海平面的高度 。

岛上雨水较多,如果相邻单元格的高度 小于或等于 当前单元格的高度,雨水可以直接向北、南、东、西流向相邻单元格。水可以从海洋附近的任何单元格流入海洋。

返回网格坐标 result 的 2D 列表 ,其中 result[i] = [ri, ci] 表示雨水从单元格 (ri, ci) 流动 既可流向太平洋也可流向大西洋 。

来源:力扣(LeetCode)
链接:https://leetcode.cn/problems/pacific-atlantic-water-flow
著作权归领扣网络所有。商业转载请联系官方授权,非商业转载请注明出处。

给一个二维矩阵,矩阵里的数字表示水的高度。矩阵的边缘是太平洋和大西洋。水流遵循高处往低处流的原则,求这个矩阵里面哪些坐标上的水能同时流动到太平洋和大西洋。

这一题也属于 flood fill 类的题目。但是这个题的做法非常巧妙,可以试着从矩阵的边缘往中间找,看看最远能找到矩阵内的哪些坐标。这些被找到的坐标上的水一定能流到两个海洋里。比如左边缘和上边缘是太平洋,就可以找 i == 0 和 j == 0 的坐标去做 DFS,并记录有哪些坐标能被遍历到。同理,右边缘和下边缘是大西洋,可以找 i == m  - 1 和 j == n - 1 的坐标去做 DFS,并记录哪些坐标能被找到。在两次DFS中都被找到的坐标,则是可以同时流向两个大洋的。

同时这一题在做DFS的时候,也跟329题类似,需要记录一个 prev 值,以判断当前坐标上的水的深度和之前遍历的坐标上的水的深度谁高谁低。因为只有高度有区别的两个坐标,才有可能实现水的流动。

时间O(mn)

空间O(mn)

Java实现

 1 class Solution {
 2     int m;
 3     int n;
 4     
 5     public List<List<Integer>> pacificAtlantic(int[][] heights) {
 6         m = heights.length;
 7         n = heights[0].length;
 8         boolean[][] pacific = new boolean[m][n];
 9         boolean[][] atlantic = new boolean[m][n];
10         for (int i = 0; i < m; i++) {
11             for (int j = 0; j < n; j++) {
12                 // pacific
13                 if (i == 0 || j == 0) {
14                     dfs(heights, pacific, i, j, heights[i][j]);
15                 }
16                 // atlantic
17                 if (i == m - 1 || j == n - 1) {
18                     dfs(heights, atlantic, i, j, heights[i][j]);
19                 }
20             }
21         }
22         
23         List<List<Integer>> res = new ArrayList<>();
24         for (int i = 0; i < m; i++) {
25             for (int j = 0; j < n; j++) {
26                 if (pacific[i][j] && atlantic[i][j]) {
27                     res.add(Arrays.asList(i, j));
28                 }
29             }
30         }
31         return res;
32     }
33     
34     private void dfs(int[][] heights, boolean[][] ocean, int i, int j, int prev) {
35         if (i < 0 || j < 0 || i >= m || j >= n || ocean[i][j] == true || heights[i][j] < prev) {
36             return;
37         }
38         ocean[i][j] = true;
39         dfs(heights, ocean, i - 1, j, heights[i][j]);
40         dfs(heights, ocean, i + 1, j, heights[i][j]);
41         dfs(heights, ocean, i, j - 1, heights[i][j]);
42         dfs(heights, ocean, i, j + 1, heights[i][j]);
43     }
44 }

 

flood fill题型总结

LeetCode 题目总结

posted @ 2020-07-23 05:33  CNoodle  阅读(249)  评论(0编辑  收藏  举报