深度优先搜索(DFS)邻接矩阵实现
代码:
// 访问标记数组,需要提前初始化为false
bool visited[MAX_VERTEX_NUM]; void DFS(AMGraph G, int v) { // 图G为邻接矩阵类型,v是当前访问的顶点// 步骤1:访问顶点vcout << v; // 输出顶点编号visited[v] = true; // 标记顶点v为已访问// 步骤2:检查v的所有邻接点for(int w = 0; w < G.vexnum; w++) { // vexnum是顶点总数// 步骤3:判断w是否是v的未访问邻接点if((G.arcs[v][w] != 0) && (!visited[w])) {// 步骤4:递归访问邻接点wDFS(G, w);}}// 步骤5:当前顶点v的所有邻接点处理完成
}
超详细执行步骤解析
假设我们有如下无向图的邻接矩阵表示(顶点0,1,2,3):
0 1 2 3 0 0 1 0 1 1 1 0 1 1 2 0 1 0 1 3 1 1 1 0
初始状态
-
visited
数组初始化为[false, false, false, false]
-
假设从顶点0开始遍历:
DFS(G, 0)
调用DFS(G, 0)
-
访问顶点0
-
输出:
0
-
visited
变为:[true, false, false, false]
-
-
检查顶点0的邻接点(w从0到3)
-
w=0:
-
G.arcs[0][0] = 0
(对角线元素,跳过)
-
-
w=1:
-
G.arcs[0][1] = 1
且visited[1]=false
-
递归调用DFS(G, 1)
-
-
调用DFS(G, 1)
-
访问顶点1
-
输出:
0 1
-
visited
变为:[true, true, false, false]
-
-
检查顶点1的邻接点
-
w=0:
-
G.arcs[1][0] = 1
但visited[0]=true
(已访问过)
-
-
w=1:
-
G.arcs[1][1] = 0
(跳过)
-
-
w=2:
-
G.arcs[1][2] = 1
且visited[2]=false
-
递归调用DFS(G, 2)
-
-
调用DFS(G, 2)
-
访问顶点2
-
输出:
0 1 2
-
visited
变为:[true, true, true, false]
-
-
检查顶点2的邻接点
-
w=0:
-
G.arcs[2][0] = 0
(跳过)
-
-
w=1:
-
G.arcs[2][1] = 1
但visited[1]=true
-
-
w=2:
-
G.arcs[2][2] = 0
(跳过)
-
-
w=3:
-
G.arcs[2][3] = 1
且visited[3]=false
-
递归调用DFS(G, 3)
-
-
调用DFS(G, 3)
-
访问顶点3
-
输出:
0 1 2 3
-
visited
变为:[true, true, true, true]
-
-
检查顶点3的邻接点
-
w=0:
-
G.arcs[3][0] = 1
但visited[0]=true
-
-
w=1:
-
G.arcs[3][1] = 1
但visited[1]=true
-
-
w=2:
-
G.arcs[3][2] = 1
但visited[2]=true
-
-
w=3:
-
G.arcs[3][3] = 0
(跳过)
-
-
递归结束,返回到DFS(G,2)
-
返回到DFS(G,2)
-
顶点2的所有邻接点已处理完毕
-
递归结束,返回到DFS(G,1)
返回到DFS(G,1)
-
继续检查w=3:
-
G.arcs[1][3] = 1
但visited[3]=true
(已访问过)
-
-
顶点1的所有邻接点已处理完毕
-
递归结束,返回到DFS(G,0)
返回到DFS(G,0)
-
继续检查w=3:
-
G.arcs[0][3] = 1
但visited[3]=true
(已访问过)
-
-
顶点0的所有邻接点已处理完毕
-
递归结束,整个DFS完成
最终遍历结果
输出序列:0 1 2 3