直接回答:扫描网格,每遇到一个未访问的陆地('1')就把岛屿计数加一,并从这个格子出发做 flood fill(DFS 或 BFS)把整块岛屿的所有陆地标记为已访问(直接改成 '0' 或另开 visited 数组)。扫完网格计数即答案。时间 O(m×n),空间最坏 O(m×n)(递归栈或队列)。
展开解析:本质是求网格隐式图的连通分量个数。实现细节:四个方向数组避免手写四段重复代码;DFS 递归在大网格下可能爆栈,可改迭代 DFS 或 BFS;允许修改输入时用原地标记省掉 visited 内存,面试中要主动说明这一副作用。并查集是第三种解法:把所有陆地向右/向下做 union,最后统计根的个数,适合「动态加陆地」的在线场景。同族变体:最大岛屿面积、被围绕的区域(从边界反向 flood fill)、腐烂的橘子(多源 BFS 求层数)。追问方向:多源 BFS 与单源 BFS 的区别、如何把网格题抽象成图论语言(节点、边、连通性)。
示例:
def num_islands(grid):
if not grid:
return 0
rows, cols, count = len(grid), len(grid[0]), 0
def sink(r, c):
if 0 <= r < rows and 0 <= c < cols and grid[r][c] == '1':
grid[r][c] = '0'
for dr, dc in ((1, 0), (-1, 0), (0, 1), (0, -1)):
sink(r + dr, c + dc)
for r in range(rows):
for c in range(cols):
if grid[r][c] == '1':
count += 1
sink(r, c)
return count