一【题目类别】
- 广度优先搜索
二【题目难度】
- 中等
三【题目编号】
- 130.被围绕的区域
四【题目描述】
- 给你一个 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”]]
六【解题思路】
- 如果从正面思考:如何将所有被围绕的区域找出来?那么这个题很难解决
- 但是如果我们从反向思考:我们通过读题可以发现,连接到边上的’O’一定是不被围绕的,其余的都是被围绕的,所以我们可以通过边上的’O’,找到所有不被围绕的,将其置为’A’
- 最后我们再将’A’还原为’O’
- 那么剩下的’O’一定都是被围绕的,只需要将其置为’X’即可
七【题目提示】
- m == board.length
- n == board[i].length
- 1 <= m, n <= 200
- board[i][j] 为 ‘X’ 或 ‘O’
八【时间频度】
- 时间复杂度: O ( n ∗ m ) O(n*m) O(n∗m),其中 m , n m,n m,n 分别是二维数组的长和宽
- 空间复杂度: O ( n ∗ m ) O(n*m) O(n∗m),其中 m , n m,n m,n 分别是二维数组的长和宽
九【代码实现】
- Java语言版
package BFS;
public class p130_SurroundedRegions {
public static void main(String[] args) {
}
private static int[] dx = {1, -1, 0, 0};
private static int[] dy = {0, 0, 1, -1};
public static void solve(char[][] board) {
int m = board.length;
int n = board[0].length;
int[][] queue = new int[m * n][2];
int front = 0;
int rear = 0;
for (int i = 0; i < n; i++) {
if (board[0][i] == 'O') {
board[0][i] = 'A';
queue[rear][0] = 0;
queue[rear++][1] = i;
}
if (board[m - 1][i] == 'O') {
board[m - 1][i] = 'A';
queue[rear][0] = m - 1;
queue[rear++][1] = i;
}
}
for (int i = 1; i < m - 1; i++) {
if (board[i][0] == 'O') {
board[i][0] = 'A';
queue[rear][0] = i;
queue[rear++][1] = 0;
}
if (board[i][n - 1] == 'O') {
board[i][n - 1] = 'A';
queue[rear][0] = i;
queue[rear++][1] = n - 1;
}
}
while (front < rear) {
int x = queue[front][0];
int y = queue[front++][1];
for (int i = 0; i < 4; i++) {
int cx = x + dx[i];
int cy = y + dy[i];
if (cx < 0 || cx >= m || cy < 0 || cy >= n || board[cx][cy] != 'O') {
continue;
}
board[cx][cy] = 'A';
queue[rear][0] = cx;
queue[rear++][1] = cy;
}
}
for (int i = 0; i < m; i++) {
for (int j = 0; j < n; j++) {
if (board[i][j] == 'A') {
board[i][j] = 'O';
} else if (board[i][j] == 'O') {
board[i][j] = 'X';
}
}
}
}
}
- C语言版
#include<stdio.h>
#include<stdlib.h>
const int dx[4] = { 1,-1,0,0 };
const int dy[4] = { 0,0,1,-1 };
void solve(char** board, int boardSize, int* boardColSize)
{
int m = boardSize;
int n = boardColSize[0];
int** queue = (int**)malloc(sizeof(int*) * (m * n));
for (int i = 0; i < (m*n); i++)
{
queue[i] = (int*)malloc(sizeof(int) * 2);
}
int front = 0;
int rear = 0;
for (int i = 0; i < m; i++)
{
if (board[i][0] == 'O')
{
board[i][0] = 'A';
queue[rear][0] = i;
queue[rear++][1] = 0;
}
if (board[i][n - 1] == 'O')
{
board[i][n - 1] = 'A';
queue[rear][0] = i;
queue[rear++][1] = n - 1;
}
}
for (int i = 1; i < n - 1; i++)
{
if (board[0][i] == 'O')
{
board[0][i] = 'A';
queue[rear][0] = 0;
queue[rear++][1] = i;
}
if (board[m - 1][i] == 'O')
{
board[m - 1][i] = 'A';
queue[rear][0] = m - 1;
queue[rear++][1] = i;
}
}
while (front < rear)
{
int x = queue[front][0];
int y = queue[front++][1];
for (int i = 0; i < 4; i++)
{
int cx = x + dx[i];
int cy = y + dy[i];
if (cx < 0 || cx >= m || cy < 0 || cy >= n || board[cx][cy] != 'O')
{
continue;
}
board[cx][cy] = 'A';
queue[rear][0] = cx;
queue[rear++][1] = cy;
}
}
for (int i = 0; i < m; i++)
{
for (int j = 0; j < n; j++)
{
if (board[i][j] == 'A')
{
board[i][j] = 'O';
}
else if (board[i][j] == 'O')
{
board[i][j] = 'X';
}
}
}
for (int i = 0; i < (m*n); i++)
{
free(queue[i]);
}
free(queue);
}
/*主函数省略*/
十【提交结果】
-
Java语言版
-
C语言版