BFS:广度优先搜索
一般用队列实现
每取出一个放入自己的距离为一的下一个(未被使用过)。
先放入A 队列: A
取出A 放入 B C 队列:B C
取出B 放入 D (不能再放C 已经使用了), 队列 C D
取出C 放入 E 队列 D E
. . .
DFS:深度优先搜索
一般用栈来实现(先进后出)
每取出一个放入自己的距离为一的下一个(未被使用过)。
先放入A 栈: A
取出A 放入 B C (先放B,再放C)栈:B C
取出C 放入 D E , 栈 B D E
取出E 没东西放 栈 B D
取出D 放F 栈B F
取F 没东西放 栈B
取B
(图摘自b站up主:正月点灯笼,具体算法细节可看其视频)
实例
该题可用深度搜索 和 广度搜索做。
深度搜索
DFS用的是栈,所以直接用递归就可以了,用的系统栈
/**
* 判断岛屿数量
* @param grid char字符型二维数组
* @return int整型
1 1 0 0 0
0 1 1 0 1
0 0 1 1 1
0 1 1 0 0
0 0 1 1 1
1 1 1 0 0
bfs 用队列
dfs 用栈
思路 记住上一排 加上
*/
public void dfs(char[][] grid,int i,int j)
{
int ni = grid.length;
int nj = grid[0].length;
if(i<0||j<0||i>=ni||j>=nj||grid[i][j]=='0')
{
return;
}
把这座岛屿所碰到过的所有1 都变为0 在主函数遍历中下一次便不会再被遍历到
grid[i][j] = '0';
dfs(grid,i-1,j);
dfs(grid,i+1,j);
dfs(grid,i,j-1);
dfs(grid,i,j+1);
}
public int solve (char[][] grid) {
// write code here
if(grid == null || grid.length == 0)
return 0;
int island = 0;
for(int i = 0; i<grid.length;i++)
{
for(int j = 0; j<grid[i].length;j++)
{
;
if(grid[i][j]=='1')
{
island ++;
dfs(grid,i,j);
}
}
}
return island;
}
不用递归的深度搜索
public int solve (char[][] grid) {
// write code here
if(grid == null || grid.length == 0)
return 0;
int island = 0;
int r = grid.length;
int c = grid[0].length;
for(int i = 0; i<r;i++)
{
for(int j = 0; j<c;j++)
{
//把这座岛屿所碰到过的所有1 都变为0;
if(grid[i][j]=='1')
{
island ++;
//dfs(grid,i,j);
Deque<Integer> stack = new LinkedList();
stack.push(i*c+j);
while(!stack.isEmpty())
{
int temp = stack.pop();
int m = temp/c;
int n = temp%c;
grid[m][n] = '0';
if((m+1)<r && grid[m+1][n] == '1')
stack.push((m+1)*c+n);
if((m-1)>=0 && grid[m-1][n] == '1')
stack.push((m-1)*c+n);
if((n+1)<c && grid[m][n+1] == '1')
stack.push(m*c+n+1);
if((n-1)>=0 && grid[m][n-1] == '1')
stack.push(m*c+n-1);
}
}
}
}
return island;
}
广度搜索 一样 只是把栈换成队列了。这边就不详写了