创建一个visited的模版
# m x n大小的矩阵
m = len(matrix)
n = len(matrix[0])
visited = [[False for _ in range(n)] for _ in range(m)]
for i in range(m):
for j in range(n):
blablabla
# DFS 模版
```python
200 岛屿数量
class Solution:
def numIslands(self, grid: List[List[str]]) -> int:
n = len(grid)
m = len(grid[0])
res = 0
visited = [[False for _ in range(m)] for _ in range(n)]
def dfs(x, y):
if x < 0 or x >= n or y < 0 or y >= m or visited[x][y] or grid[x][y] == '0':
return
visited[x][y] = True
dfs(x-1, y)
dfs(x+1, y)
dfs(x, y-1)
dfs(x, y+1)
for i in range(n):
for j in range(m):
if grid[i][j] == '1' and not visited[i][j]:
res += 1
dfs(i, j)
return res
主要的地方是res在哪里加, dfs的直接返回情况有哪些(一定要注意or grid[x][y] == ‘0’)
695 岛屿的最大面积
这个地方的区别就在于在哪里进行面积+=1的操作, 实际上本方法用的是递归
return 1 + dfs(x-1, y) + dfs(x+1, y) + dfs(x, y-1) + dfs(x, y+1)
class Solution:
def maxAreaOfIsland(self, grid: List[List[int]]) -> int:
n = len(grid)
m = len(grid[0])
visited = [[False for _ in range(m)] for _ in range(n)]
def dfs(x, y):
if x < 0 or x >= n or y < 0 or y >= m or visited[x][y] or grid[x][y] == 0:
return 0
visited[x][y] = True
return 1 + dfs(x-1, y) + dfs(x+1, y) + dfs(x, y-1) + dfs(x, y+1)
res = 0
for i in range(n):
for j in range(m):
if grid[i][j] == 1 and not visited[i][j]:
res = max(res, dfs(i, j))
return res
当然不这样递归也可以, 但就需要对每一个递归开始初始化一个global variable
def dfs(grid, visited, x, y):
"""
深度优先搜索,对一整块陆地进行标记
"""
global count # 定义全局变量,便于传递count值
for i, j in position:
cur_x = x + i
cur_y = y + j
# 下标越界,跳过
if cur_x < 0 or cur_x >= len(grid) or cur_y < 0 or cur_y >= len(grid[0]):
continue
if not visited[cur_x][cur_y] and grid[cur_x][cur_y] == 1:
visited[cur_x][cur_y] = True
count += 1
dfs(grid, visited, cur_x, cur_y)
463 岛屿的周长
class Solution:
def islandPerimeter(self, grid: List[List[int]]) -> int:
m, n = len(grid), len(grid[0])
def dfs(i, j):
if i < 0 or j < 0 or i >= m or j >= n or grid[i][j] == 0:
return 1
if grid[i][j] == 2: # 已访问
return 0
grid[i][j] = 2 # 标记为已访问
return (dfs(i-1, j) +
dfs(i+1, j) +
dfs(i, j-1) +
dfs(i, j+1))
total_perimeter = 0
for i in range(m):
for j in range(n):
if grid[i][j] == 1:
total_perimeter += dfs(i, j)
return total_perimeter
虽然写的是easy但一点都不easy好吧, 什么时候多加1呢? 当dfs每经过一个水域或者边界的时候, 就会增加1
994 腐烂的橘子
class Solution:
def orangesRotting(self, grid: List[List[int]]) -> int:
R, C = len(grid), len(grid[0])
# queue - all starting cells with rotting oranges
queue = collections.deque()
for r, row in enumerate(grid):
for c, val in enumerate(row):
if val == 2:
queue.append((r, c, 0))
def neighbors(r, c) -> (int, int):
for nr, nc in ((r - 1, c), (r, c - 1), (r + 1, c), (r, c + 1)):
if 0 <= nr < R and 0 <= nc < C:
yield nr, nc
d = 0
while queue:
r, c, d = queue.popleft()
for nr, nc in neighbors(r, c):
if grid[nr][nc] == 1:
grid[nr][nc] = 2
queue.append((nr, nc, d + 1))
if any(1 in row for row in grid):
return -1
return d