417. 太平洋大西洋水流问题
题目
有一个 m × n
的矩形岛屿,与 太平洋 和 大西洋 相邻。 “太平洋” 处于大陆的左边界和上边界,而 “大西洋” 处于大陆的右边界和下边界。
这个岛被分割成一个由若干方形单元格组成的网格。给定一个 m x n
的整数矩阵 heights
, heights[r][c]
表示坐标 (r, c)
上单元格 高于海平面的高度 。
岛上雨水较多,如果相邻单元格的高度 小于或等于 当前单元格的高度,雨水可以直接向北、南、东、西流向相邻单元格。水可以从海洋附近的任何单元格流入海洋。
返回网格坐标 result
的 2D 列表 ,其中 result[i] = [ri, ci]
表示雨水从单元格 (ri, ci)
流动 既可流向太平洋也可流向大西洋 。
示例 1:
输入: 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]] 输出: [[0,4],[1,3],[1,4],[2,2],[3,0],[3,1],[4,0]]
示例 2:
输入: heights = [[2,1],[1,2]] 输出: [[0,0],[0,1],[1,0],[1,1]]
提示:
m == heights.length
n == heights[r].length
1 <= m, n <= 200
0 <= heights[r][c] <= 105
思路
题目的意思是要找既可以流入太平洋又可以流入大西洋的地块,所以我们可以从边界开始找比自己还要大的单元格,从太平洋的左边界和上边界出发,找比自己大的单元格,标记出所有能让水流入太平洋的单元格;从大西洋的右边界和下边界出发,也是找比自己大的单元格,标记出所有能让水流入大西洋的单元格。最后判断单元格是否同时被标记为能流向太平洋和大西洋,符合条件就可以加入结果数组。
代码
class Solution {
public:vector<vector<int>> d,t,ans;//d和t分别标记可以流向太平洋和大西洋的单元格int n,m;// n 和 m 分别表示矩阵的行数和列数void dfs(vector<vector<int>>& heights, vector<vector<int>>& visited, int i, int j) { if(visited[i][j]==1) return;//单元格已经被访问过,直接返回visited[i][j] = 1;//标记为已访问//单元格既可以流向太平洋又可以流向大西洋if(d[i][j]&&t[i][j]) ans.push_back({i,j}); //上下左右搜索大于等于当前格高度的单元格if(i-1>=0&&heights[i-1][j]>=heights[i][j]) dfs(heights,visited,i-1,j);if(i+1<n&&heights[i+1][j]>=heights[i][j]) dfs(heights,visited,i+1,j); if(j-1>=0&&heights[i][j-1]>=heights[i][j]) dfs(heights,visited,i,j-1);if(j+1<m&&heights[i][j+1]>=heights[i][j]) dfs(heights,visited,i,j+1); }vector<vector<int>> pacificAtlantic(vector<vector<int>>& heights) {n=heights.size(),m=heights[0].size();d=t=vector<vector<int>>(n,vector<int>(m,0));//初始化//从太平洋左上,大西洋右下边界开始搜索for(int i=0;i<n;++i) dfs(heights,d,i,0);for(int i=0;i<n;++i) dfs(heights,t,i,m-1);for(int j=0;j<m;++j) dfs(heights,d,0,j);for(int j=0;j<m;++j) dfs(heights,t,n-1,j);return ans;}
};