- DFS模板:
1 void dfs(int step) { 2 if (...) //判断边界,到达边界则返回 3 return; 4 for (循环所有方向) { 5 if (...) { //可能需要判断条件 6 book[...] = 1; //标记 7 dfs(step+1); 8 book[...] = 0; //取消标记 9 } 10 } 11 }
- 用DPS遍历图。我们用一个二维数组e来储存图。
我们用上面二维数组中的(i, j)储存的数字来表示顶点i到顶点j是否有边——1表示有边,∞表示没有边,0表示自己到自己(即i等于j)。1 //图的遍历 - 深度优先 2 #include <stdio.h> 3 int book[101], sum, n, e[101][101]; 4 5 void dfs(int cur) { //cur是当前所在的顶点编号 6 int i; 7 printf("%d ", cur); 8 sum++; //每访问一个点,sum就加1 9 if (sum == n) return; //所有的顶点都已经访问过则直接退出 10 for (i = 1; i <= n; i++) { //从1号顶点n号顶点依次尝试,看哪些顶点与当前顶点cur有边相连 11 //判断当前顶点cur到顶点i是否有边,并判断顶点i是否已访问过 12 if (e[cur][i] == 1 && book[i] == 0) { 13 book[i] = 1; //标记顶点i已经访问过 14 dfs(i); //从顶点i再出发继续遍历 15 } 16 } 17 return; 18 } 19 20 int main() { 21 int i, j, m, a, b; 22 scanf("%d %d", &n, &m); 23 //初始化二维矩阵 24 for (i = 1; i <= n; i++) 25 for (j = 1; j <= n; j++) 26 if (i == j) 27 e[i][j] = 0; 28 else 29 e[i][j] = 99999999; //我们这里假设99999999为正无穷 30 31 //读入顶点之间的边 32 for (i = 1; i <= m; i++) { 33 scanf("%d %d", &a, &b); 34 e[a][b] = 1; 35 e[b][a] = 1; //这里是无向图,所以需要将e[b][a]也赋为1 36 } 37 38 //从1号顶点出发 39 book[1] = 1; //标记1号顶点已访问 40 dfs(1); //从1号顶点开始遍历 41 42 return 0; 43 }
结果如下:
- BFS模板:
1 while (head < tail) { 2 for(循环所有方向) { 3 if (可能需要判断条件) { 4 ... //更新当前坐标 5 if (...) continue; //判断所有不可能的情况,不可能就continue 6 book[...] = 1; //标记 7 tail++; 8 } 9 } 10 head++; 11 }
- 用BFS遍历图:
1 //图的遍历 - 广度优先 2 #include <stdio.h> 3 4 int main() { 5 int i, j, n, m, a, b, cur, book[101] = {0}, e[101][101]; 6 int que[10001], head, tail; 7 scanf("%d %d", &n, &m); 8 //初始化二维矩阵 9 for (i = 1; i <= n; i++) 10 for (j = 1; j <= n; j++) 11 if (i == j) 12 e[i][j] = 0; 13 else 14 e[i][j] = 99999999; 15 16 //读入顶点之间的边 17 for (i = 1; i <= m; i++) { 18 scanf("%d %d", &a, &b); 19 e[a][b] = 1; 20 e[b][a] = 1; 21 } 22 23 //队列初始化 24 head = 1; 25 tail = 1; 26 27 //从1号顶点出发,将1号顶点加入队列 28 que[tail] = 1; 29 tail++; 30 book[1] = 1; //标记1号顶点已访问 31 32 //当队列不为空时,循环 33 while (head < tail) { 34 cur = que[head]; //当前正在访问的顶点编号 35 for (i = 1; i <= n; i++) { //从1~n依次尝试 36 //判断从顶点cur到顶点i有边,并且顶点i没有被访问过,则将顶点i入队 37 if (e[cur][i] == 1 && book[i] == 0) { 38 que[tail] = i; 39 tail++; 40 book[i] = 1; //标记顶点i已访问 41 } 42 //如果tail大于n,则表明所有顶点都已经被访问过 43 if (tail > n) { 44 break; 45 } 46 head++; //不要忘记,一个顶点扩展结束后,head++,然后才能继续往下扩展 47 } 48 49 for (i = 1; i < tail; i++) 50 printf("%d ", que[i]); 51 return 0; 52 } 53 }
结果如下: