【算法分析与设计】被围绕的区域

       📝个人主页:五敷有你      

 🔥系列专栏:算法分析与设计

⛺️稳中求进,晒太阳

题目

给你一个 m x n 的矩阵 board ,由若干字符 'X' 和 'O' ,找到所有被 'X' 围绕的区域,并将这些区域里所有的 'O' 用 'X' 填充。

示例

示例 1:

输入:board = [["X","X","X","X"],["X","O","O","X"],["X","X","O","X"],["X","O","X","X"]]
输出:[["X","X","X","X"],["X","X","X","X"],["X","X","X","X"],["X","O","X","X"]]
解释:被围绕的区间不会存在于边界上,换句话说,任何边界上的 'O' 都不会被填充为 'X'。 任何不在边界上,或不与边界上的 'O' 相连的 'O'
 最终都会被填充为 'X'
。如果两个元素在水平或垂直方向相邻,则称它们是“相连”的。

示例 2:

输入:board = [["X"]]
输出:[["X"]]

思路(dfs+递归)

图中就有三种状态

  • x
  • 被x包围的O
  • 没有被x包围的O

体中要求把所有被x包围的O换成X,没有被X包围的O不用理会。

那么想直接找被X包围O很难,因为被X包围的O不知有一个,可能连成片,所以想直接找上下左右判断不切时间,pass

那就想到用边缘的O,来做深度优先遍历,这样,一路上所有的O都是不符合条件的,让他改为其他字符。

之后遍历所有字符,找到O改为x,并将其他字符改回O。

代码实现

class Solution {
    public void solve(char[][] board) {
         int row=board.length;
         int col=board[0].length;
            for(int i=0;i<row;i++){
               dfs(board,i,0);
               dfs(board,i,col-1);
            }
            for(int i=1;i<col-1;i++){
               dfs(board,0,i);
               dfs(board,row-1,i);
            }
            for(int i=0;i<row;i++){
                for(int j=0;j<col;j++){
                     
                    if(board[i][j]=='O'){
                        board[i][j]='X';
                    }else if(board[i][j]=='z'){
                        board[i][j]='O';
                    }
                 
                }
            }

    }
    public static void dfs(char[][] board,int row,int col){
         if(row<0||col<0||row>=board.length||col>=board[0].length|| board[row][col] !='O'){
             return;
         }

       board[row][col]='z';
         dfs(board,row-1,col);
          dfs(board,row,col+1);
           dfs(board,row+1,col);
            dfs(board,row,col-1);
    }
}

运行结果

时间复杂度:O(n×m),其中 n 和 m 分别为矩阵的行数和列数。深度优先搜索过程中,每一个点至多只会被标记一次。

空间复杂度:O(n×m),其中 n 和 m 分别为矩阵的行数和列数。主要为深度优先搜索的栈的开销。

  • 27
    点赞
  • 26
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 2
    评论
评论 2
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

打赏作者

五敷有你

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

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

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

打赏作者

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

抵扣说明:

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

余额充值