思路:
依题意,只要某个区域包含边界的'O'
那么这个区域就不能被'X'
所填充。根据这一发现,我们只要搜索每一个区域,判断它是否包含边界的'O'
,就能确定出需要被'X'
填充的区域!
边界'O'
的判断条件是为i == nr - 1 || j == nc - 1 || i == 0 || j == 0) && board[i][j] == 'O'
。
根据以上分析,我们可以遍历整个二维数组,每当遇到一个'O'
我们就对这个'O'
进行dfs,同时判断是否包含边界的'O'
,dfs完当前的位置后,我们可以知道当前位置区域是否包含边界的'O'
,如果包含我们不对该区域进行填充,如果不包含,再调用dfs对该区域进行填充。
class Solution {
boolean is_Suround = true; //设置标志为,记录当前区域是否包含了边界的X,默认为是
public void dfs(char[][] board,int i, int j){
int nr = board.length;
int nc = board[0].length;
if(i >= nr || j >= nc || i < 0 || j < 0 || board[i][j] != 'O') return;
if((i == nr - 1 || j == nc - 1 || i == 0 || j == 0) && board[i][j] == 'O'){ //如果包含了边界O设置is_Suround为false
is_Suround = false;
}
board[i][j] = 'A';//为了dfs顺利执行,先设置该位置为A,因为返回条件有board[i][j] != 'O',如果不设置会栈溢出
dfs(board, i - 1, j); //上下左右进行dfs
dfs(board, i + 1, j);
dfs(board, i, j - 1);
dfs(board, i, j + 1);
}
public void dfs_fix(char[][] board,int i, int j){ //该函数为填充被包围的区域
int nr = board.length;
int nc = board[0].length;
if(nr == 0)
return;
if(i >= nr || j >= nc || i < 0 || j < 0 || board[i][j] == 'X') return;
board[i][j] = 'X';
dfs_fix(board, i - 1, j);
dfs_fix(board, i + 1, j);
dfs_fix(board, i, j - 1);
dfs_fix(board, i, j + 1);
}
public void solve(char[][] board) {
int nr = board.length;
int nc = board[0].length;
for(int i = 0; i < nr; i++){
for(int j = 0; j < nc; j++){
if(board[i][j] == 'O'){ //如果是O,则dfs整个区域
dfs(board,i,j);
if(flog){ //如果区域没有包含边界,填充
dfs_fix(board,i,j);
}
}
is_Suround = true;
}
}
for(int i = 0; i < nr; i++){ //修改A为O
for(int j = 0; j < nc; j++){
if(board[i][j] == 'A'){
board[i][j] = 'O';
}
}
flog = true;
}
}
}