统计封闭岛屿的数目
问题描述:
有一个二维矩阵 grid ,每个位置要么是陆地(记号为 0 )要么是水域(记号为 1 )。
我们从一块陆地出发,每次可以往上下左右 4 个方向相邻区域走,能走到的所有陆地区域,我们将其称为一座「岛屿」。
如果一座岛屿完全由水域包围,即陆地边缘上下左右所有相邻区域都是水域,那么我们将其称为 「封闭岛屿」。
请返回封闭岛屿的数目。
示例1:
![](https://i-blog.csdnimg.cn/blog_migrate/d97b81076f0c168fbd906b1662d08424.png)
输入:grid = [[1,1,1,1,1,1,1,0],[1,0,0,0,0,1,1,0],[1,0,1,0,1,1,1,0],[1,0,0,0,0,1,0,1],[1,1,1,1,1,1,1,0]]
输出:2
解释:
灰色区域的岛屿是封闭岛屿,因为这座岛屿完全被水域包围(即被 1 区域包围)。
示例2:
![](https://i-blog.csdnimg.cn/blog_migrate/af5b87a831afcd02c4a7d0b173412227.png)
输入:grid = [[1,1,1,1,1,1,1],
[1,0,0,0,0,0,1],
[1,0,1,1,1,0,1],
[1,0,1,0,1,0,1],
[1,0,1,1,1,0,1],
[1,0,0,0,0,0,1],
[1,1,1,1,1,1,1]]
输出:2
解题思路:
首先我们需要遍历整个岛屿,如果当前位置为0(陆地),我们就需要判断该位置所在的岛屿是否为封闭岛屿。dfs上下左右四个方向,如果四个方向全部都是陆地,则返回真,总数+1。(注意:dfs的时候需要把碰到陆地标记为水域,这样就可以避免下一次遍历的时候重复计算了)
此题不需要回溯,因为是求同一区域,不需要计算路径。
图解:
第一次从左上角开始进入dfs
![](https://i-blog.csdnimg.cn/blog_migrate/92554f6ef52d8324077e60848664b26d.png)
(1)变为1,并从四个方向dfs
![](https://i-blog.csdnimg.cn/blog_migrate/4ebe33260be9092f0a88ef7349bc7ee5.png)
![](https://i-blog.csdnimg.cn/blog_migrate/880835c2c43474ef50a2cee61aec8442.png)
![](https://i-blog.csdnimg.cn/blog_migrate/f92f8d155fade2fa0433dbc741c3844c.png)
![](https://i-blog.csdnimg.cn/blog_migrate/1e389bd1f72abdeb0a46ec7699431758.png)
(2)第一次返回0,并把陆地0都变成了水域1.
![](https://i-blog.csdnimg.cn/blog_migrate/42fdbcf50b0e7155f3d8a7cfe0087c7e.png)
(3)当进入四周都是水域的陆地时,返回1
![](https://i-blog.csdnimg.cn/blog_migrate/cfccfd7529247d31014caacfbfeec2ab.png)
代码如下:
#include<iostream>
#include<vector>
using namespace std;
int dfs(int i,int j,vector<vector<int> >& grid){
if(i<0||j<0||i>=grid.size()||j>=grid[i].size()){//不满足条件
return 0;
}
if(grid[i][j]==1){//如果碰到水域返回1
return 1;
}
grid[i][j]=1;//如果碰到陆地则标记为水域
int x1= dfs(i+1,j,grid);
int x2= dfs(i-1,j,grid);
int y1= dfs(i,j+1,grid);
int y2= dfs(i,j-1,grid);
//四个方向全为水域返回1
if(x1&&x2&&y1&&y2){
return 1;
}
return 0;
}
int closedIsland(vector<vector<int> >& grid) {
int sum=0;
for(int i=1;i<grid.size()-1;i++){//边缘部分肯定不是岛屿,所以从1开始
for(int j=1;j<grid[i].size()-1;j++){
if(grid[i][j]==0){ //如果是陆地
if(dfs(i,j,grid)){
sum++;
}
}
}
}
return sum;
}
int main(){
vector<vector<int> > grid={{0,0,1,1,0,1,0,0,1,0},{1,1,0,1,1,0,1,1,1,0},{1,0,1,1,1,0,0,1,1,0},{0,1,1,0,0,0,0,1,0,1},{0,0,0,0,0,0,1,1,1,0},{0,1,0,1,0,1,0,1,1,1},{1,0,1,0,1,1,0,0,0,1},{1,1,1,1,1,1,0,0,0,0},{1,1,1,0,0,1,0,1,0,1},{1,1,1,0,1,1,0,1,1,0}};
cout<<closedIsland(grid);
return 0;
}