1. 矩阵或图上的DFS
200. 岛屿数量
from collections import deque
class Solution:
# # x-1,y
# # x,y-1 x,y x,y+1
# # x+1,y
# # 方向数组,它表示了相对于当前位置的 4 个方向的横、纵坐标的偏移量,这是在图上进行DFS和BFS的常见技巧
directions = [(-1, 0), (0, -1), (1, 0), (0, 1)]
### DFS 时间:O(mn) 空间最坏:O(mn)整个图全为1
def numIslands(self, grid: List[List[str]]) -> int:
m=len(grid)
if m==0: ###边界条件判断,必须放在n之前, 因为m=0时grid[0]就不存在,n就会报错
return 0
n=len(grid[0])
marked=[[False]*n for _ in range(m)] #标记数组,初始化为所有点最开始都未被访问过
count=0 #统计一共有几个点可以进行一次完整的DFS就有有几个岛屿
## 从第 1 行、第 1 格开始,对每一格尝试进行一次 DFS 操作
for i in range(m):
for j in range(n):
if not marked[i][j] and grid[i][j]=='1': #要想进行DFS需要是 未被标记过的’1‘ ,每进入DFS的’1‘会影响grid中之后点的marked,所以整个grid中可能只有n个’1‘可以进行DFS(也就有n个岛屿)
self.dfs(i, j, m, n, marked, grid) #####self. ,这里只有传入的marked数组List需要进行修改
count+=1
return count
def dfs(self, i, j, m, n, marked, grid):
marked[i][j]=True #每个进入DFS的点都要首先被标记访问过了
### 注意:这里没有注明nonlocal就可以直接改变marked, 是因为marked是数组List而List是可变的对象, 但若要修改int,string就必须要首先声明unlocal
for d in self.directions: ###########注意是 self.directions,因为directions是在类里面定义的,每个位置有四种选择
new_i=i+d[0]
new_j=j+d[1]
if 0<= new_i
self.dfs(new_i, new_j, m, n, marked, grid) #这样递归使每次都可以沿一个方向一直找下去
### BFS 时间:O(mn) 空间最坏:O(min(m,n))整个图全为1
def numIslands(self, grid: List[List[str]]) -> int:
m=len(grid)
if m==0:
return 0
n=len(grid[0])
marked=[[False]*n for i in range(m)]
count=0
for i in range(m):
for j in range(n):
if not marked[i][j] and grid[i][j]=='1': #能进入这个if就说明该点可以进行一次BFS(就是一个岛屿)
next_queue=[(i,j)]#以该点为起始点进行BFS,
marked[i][j]=True #并且该点首先被标记访问过了
while next_queue:
now_i, now_j=next_queue.pop(0)
for d in self.directions:
new_i=now_i+d[0]
new_j=now_j+d[1]
if 0<= new_i
next_queue.append((new_i,new_j))
marked[new_i][new_j]=True
count+=1
return count
### BFS详解
def numIslands(self, grid: List[List[str]]) -> int:
m = len(grid)
# 特判
if m == 0:
return 0
n = len(grid[0])
marked = [[False for _ in range(n)] for _ in range(m)]
count = 0
# 从第 1 行、第 1 格开始,对每一格尝试进行一次 BFS 操作
for i in ran