深度优先和广度优先

1.题目(力扣934)

在给定的二维二进制数组 A 中,存在两座岛。(岛是由四面相连的 1 形成的一个最大组。)现在,我们可以将 0 变为 1,以使两座岛连接起来,变成一座岛。返回必须翻转的 0 的最小数目。(可以保证答案至少是 1。)

解析:先深度优先搜索(DFS)找到一个岛屿,再广度优先搜索(BFS)查找需要翻转的0的最小数目。

class Solution {
private:
  queue<pair<int,int>> point;
public:
    //模板1:深度优先搜索模板
   void dfs(queue<pair<int,int>>& point,vector<vector<int>>& grid,int i,int j){
       int row=grid.size();
       int col=grid[0].size();
       grid[i][j]=2;//
       point.push({i,j});
       if(i-1>=0&&grid[i-1][j]==1)
        dfs(point,grid,i-1,j);
       if(i+1<row&&grid[i+1][j]==1)
        dfs(point,grid,i+1,j);
       if(j-1>=0&&grid[i][j-1]==1)
        dfs(point,grid,i,j-1);
       if(j+1<col&&grid[i][j+1]==1)
         dfs(point,grid,i,j+1);
   }

    int shortestBridge(vector<vector<int>>& A) {
        int row=A.size();
        int col=A[0].size();
        bool visited=false;
        for(int i=0;i<row;i++){
            if(visited)break;
            for(int j=0;j<col;j++){
                if(A[i][j]==1){
                    dfs(point,A,i,j);
                    visited=true;
                    break;
                }
            }
        }
         //模板二:广度优先搜索模板
        int step=0;
        int dirr[4]={-1,0,1,0};
        int dirc[4]={0,-1,0,1};
        while(!point.empty()){
            int size=point.size();
            for(int i=0;i<size;i++){
                auto temp=point.front();
                point.pop();
                for(int i=0;i<4;i++){
                    int x=dirc[i]+temp.first;
                    int y=dirr[i]+temp.second;  
                     if(x<0||x>=row||y<0||y>=col)
                       continue;     
                    if(A[x][y]==2) 
                    continue;                                                                        
                    if(A[x][y]==1)
                     return step;
                    A[x][y]=2;
                    point.push({x,y});
                }
            }
              step++;
        }
      return step;
        
    }

};

2.题目(力扣面试题:水域大小)

你有一个用于表示一片土地的整数矩阵land,该矩阵中每个点的值代表对应地点的海拔高度。若值为0则表示水域。由垂直、水平或对角连接的水域为池塘。池塘的大小是指相连接的水域的个数。编写一个方法来计算矩阵中所有池塘的大小,返回值需要从小到大排序。

输入:
[
  [0,2,1,0],
  [0,1,0,1],
  [1,1,0,1],
  [0,1,0,1]
]
输出: [1,2,4]

解析:深度优先搜索找到所有水域即可(注意与模板不同的是:对角线也得搜索)。

class Solution {
private:
  vector<int> result{};
  int num=0;
public:
    void dfs(vector<vector<int>>& land,int i,int j){
        int row=land.size();
        int col=land[0].size();
        num++;
        land[i][j]=1;
        if(i-1>=0&&land[i-1][j]==0)   dfs(land,i-1,j);
        if(i+1<row&&land[i+1][j]==0)  dfs(land,i+1,j);
        if(j-1>=0&&land[i][j-1]==0)   dfs(land,i,j-1);
        if(j+1<col&&land[i][j+1]==0)   dfs(land,i,j+1);
        if(i-1>=0&&j-1>=0&&land[i-1][j-1]==0)  dfs(land,i-1,j-1);
        if(i+1<row&&j+1<col&&land[i+1][j+1]==0)  dfs(land,i+1,j+1);
        if(i-1>=0&&j+1<col&&land[i-1][j+1]==0)   dfs(land,i-1,j+1);
        if(i+1<row&&j-1>=0&&land[i+1][j-1]==0)   dfs(land,i+1,j-1);
    }
    vector<int> pondSizes(vector<vector<int>>& land) {
        for(int i=0;i<land.size();i++){
            for(int j=0;j<land[0].size();j++){
                if(land[i][j]==0){
                dfs(land,i,j);
                result.push_back(num);
                num=0;
                }
            }
        }
        sort(result.begin(),result.end());
        return result;

    }
};
  • 1
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

SCUT慎独

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值