【LeetCode-搜索】岛屿数量
题目描述
给你一个由 '1'(陆地)和 '0'(水)组成的的二维网格,请你计算网格中岛屿的数量。
岛屿总是被水包围,并且每座岛屿只能由水平方向和/或竖直方向上相邻的陆地连接形成。
此外,你可以假设该网格的四条边均被水包围。
示例:
输入:
11110
11010
11000
00000
输出: 1
输入:
11000
11000
00100
00011
输出: 3
解释: 每座岛屿只能由水平和/或竖直方向上相邻的陆地连接而成。
题目链接: https://leetcode-cn.com/problems/number-of-islands/
思路
使用dfs。dfs的起点为没有访问过并且值为1的位置。代码如下:
class Solution {
public:
int dirs[4][2] = {{0,1},{1,0},{0,-1},{-1,0}};
int numIslands(vector<vector<char>>& grid) {
if(grid.empty()) return 0;
int rows = grid.size();
int cols = grid[0].size();
vector<vector<int>> visit(rows, vector<int>(cols, 0));
int cnt = 0;
for(int i=0; i<rows; i++){
for(int j=0; j<cols; j++){
if(!visit[i][j] && grid[i][j]=='1'){
dfs(grid, i, j, rows, cols, visit);
cnt++;
}
}
}
return cnt;
}
void dfs(vector<vector<char>> grid, int r, int c, int rows, int cols, vector<vector<int>>& visit){
visit[r][c] = 1;
for(int i=0; i<4; i++){
int nr = r+dirs[i][0];
int nc = c+dirs[i][1];
if(nr>=0 && nr<rows && nc>=0 && nc<cols && grid[nr][nc]=='1' && !visit[nr][nc]){
dfs(grid, nr, nc, rows, cols, visit);
}
}
}
};
// 超时
该方法由于超时未通过。
如果把visit数组删掉,通过将grid[i][j]改为'0'表示已经访问过则可以通过。代码如下:
class Solution {
public:
int dirs[4][2] = {{0,1},{1,0},{0,-1},{-1,0}};
int numIslands(vector<vector<char>>& grid) {
if(grid.empty()) return 0;
int rows = grid.size();
int cols = grid[0].size();
int cnt = 0;
for(int i=0; i<rows; i++){
for(int j=0; j<cols; j++){
if(grid[i][j]=='1'){
dfs(grid, i, j, rows, cols);
cnt++;
}
}
}
return cnt;
}
void dfs(vector<vector<char>>& grid, int r, int c, int rows, int cols){
grid[r][c] = '0';
for(int i=0; i<4; i++){
int nr = r+dirs[i][0];
int nc = c+dirs[i][1];
if(nr>=0 && nr<rows && nc>=0 && nc<cols && grid[nr][nc]=='1'){
dfs(grid, nr, nc, rows, cols);
}
}
}
};
- 时间复杂度:O(mn)
m,n分别为行列数。 - 空间复杂度:O(mn)
当grid全为1时,栈的深度为mn.