首页 > 代码库 > 第四章 搜索(深度、广度搜索、全排列、走迷宫、再解炸弹人、宝岛探险、水管工游戏)
第四章 搜索(深度、广度搜索、全排列、走迷宫、再解炸弹人、宝岛探险、水管工游戏)
一、深度优先搜索DFS
深度优先搜索DFS的关键思想是:当下应该怎么做(每个方法都试一遍),这一步解决后,进入下一步,下一步的解决方法和这一步的解决方法是一样的
DFS的基本模型
void dfs(int step)
{
判断边界
尝试每一种可能 for(i=1;i<=n;i++)
{
继续下一步 dfs(step+1)
}
返回
}
1.1全排列
1 //输入一个数n 2 //输出1-n的全排列 3 #include <stdio.h> 4 int n, book[10], a[10]; 5 void dfs(int step) 6 { 7 int i; 8 if (step > n) 9 { 10 for (i = 1;i <= n;i++) 11 { 12 printf("%d ",a[i]); 13 } 14 printf("\n"); 15 return; 16 } 17 for (i = 1;i <= n;i++) 18 { 19 if (book[i] == 0) 20 { 21 a[step] = i; 22 book[i] = 1; 23 dfs(step+1); 24 book[i] = 0; 25 } 26 } 27 return; 28 } 29 int main() 30 { 31 scanf("%d",&n); 32 dfs(1); 33 return 0; 34 }
1.2两个三位数相加的结果是三位数,这9个数字各不相同,_ _ _ + _ _ _ = _ _ _
1 #include <stdio.h> 2 int total = 0; 3 int book[10], a[10]; 4 void dfs(int step) 5 { 6 int i; 7 if (step == 10) 8 { 9 if (100 * (a[1] + a[4]) + 10 * (a[2] + a[5]) + a[3] + a[6] == 100 * a[7] + 10 * a[8] + a[9]) 10 { 11 total++; 12 printf("%d%d%d + %d%d%d = %d%d%d\n",a[1],a[2],a[3],a[4],a[5],a[6],a[7],a[8],a[9]); 13 } 14 return; 15 } 16 for (i = 1;i < 10;i++) 17 { 18 if (book[i] == 0) 19 { 20 book[i] = 1; 21 a[step] = i; 22 dfs(step+1); 23 book[i] = 0; 24 } 25 } 26 return; 27 } 28 int main() 29 { 30 dfs(1); 31 printf("%d\n",total/2); 32 return 0; 33 }
1.3走迷宫,解救小哈
1 #include <stdio.h> 2 int n, m, map[10][10], book[10][10],endx, endy,minstep=978978; 3 void dfs(int x, int y, int step) 4 { 5 int i,tx,ty; 6 int next[4][2] = { {0,1},{1,0},{0,-1},{-1,0} }; 7 if (x == endx&&y == endy) 8 { 9 if (minstep > step) 10 minstep = step; 11 return; 12 } 13 for (i = 0;i < 4;i++) 14 { 15 tx = x + next[i][0]; 16 ty = y + next[i][1]; 17 if (tx<1 || ty<1 || tx>n || ty>m) 18 continue; 19 if (map[tx][ty] == 0 && book[tx][ty] == 0) 20 { 21 book[tx][ty] = 1; 22 dfs(tx,ty,step+1); 23 book[tx][ty] = 0; 24 } 25 } 26 return; 27 } 28 int main() 29 { 30 int i, j, startx, starty; 31 scanf("%d%d",&n,&m); 32 for (i = 1;i <= n;i++) 33 { 34 for (j = 1;j <= m;j++) 35 { 36 scanf("%d",&map[i][j]); 37 } 38 } 39 scanf("%d%d%d%d",&startx,&starty,&endx,&endy); 40 41 dfs(startx,starty,0); 42 43 printf("%d\n",minstep); 44 return 0; 45 }
二、广度优先搜索BFS
深度优先搜索DFS——递归
广度优先搜索BFS——队列
继续走迷宫
1 #include <stdio.h> 2 int n, m, endx, endy; 3 int map[10][10], book[10][10]; 4 struct node 5 { 6 int x; 7 int y; 8 int step; 9 }; 10 void bfs(int startx,int starty) 11 { 12 struct node queue[100]; 13 int head, tail; 14 int next[4][2] = { {0,1},{1,0},{0,-1},{-1,0} }; 15 int i, tx, ty, flag = 0; 16 head = 1;tail = 1; 17 queue[tail].x = startx; 18 queue[tail].y = starty; 19 queue[tail].step = 0; 20 tail++; 21 book[startx][starty] = 1; 22 while (head<tail) 23 { 24 for (i = 0;i < 4;i++) 25 { 26 tx = queue[head].x + next[i][0]; 27 ty = queue[head].y + next[i][1]; 28 if (tx<1 || ty<1 || tx>n || ty>m) 29 { 30 continue; 31 } 32 if (map[tx][ty] == 0 && book[tx][ty] == 0) 33 { 34 book[tx][ty] = 1; 35 queue[tail].x = tx; 36 queue[tail].y = ty; 37 queue[tail].step = queue[head].step + 1; 38 tail++; 39 } 40 if (tx == endx&&ty == endy) 41 { 42 flag = 1; 43 break; 44 } 45 } 46 if (flag == 1) 47 break; 48 head++; 49 } 50 printf("%d\n",queue[tail-1].step); 51 52 } 53 int main() 54 { 55 int i, j,startx,starty; 56 scanf("%d%d",&n,&m); 57 for (i = 1;i <= n;i++) 58 { 59 for (j = 1;j <= m;j++) 60 { 61 scanf("%d",&map[i][j]); 62 } 63 } 64 scanf("%d%d%d%d",&startx,&starty,&endx,&endy); 65 bfs(startx,starty); 66 return 0; 67 }
三、再解炸弹人
现在炸弹不是想放在那里就能放在那里的了,必须由小人能够走到的地方才能放置炸弹。比如下面这个例子小人默认站在(3,3)这个位置。请问放在何处最多可以消灭多个敌人。
输入
13 13 3 3
#############
#GG.GGG#GGG.#
###.#G#G#G#G#
#.......#..G#
#G#.###.#G#G#
#GG.GGG.#.GG#
#G#.#G#.#.#.#
##G...G.....#
#G#.#G###.#G#
#...G#GGG.GG#
#G#.#G#G#.#G#
#GG.GGG#G.GG#
#############
#############
#GG.GGG#GGG.#
###.#G#G#G#G#
#.......#..G#
#G#.###.#G#G#
#GG.GGG.#.GG#
#G#.#G#.#.#.#
##G...G.....#
#G#.#G###.#G#
#...G#GGG.GG#
#G#.#G#G#.#G#
#GG.GGG#G.GG#
#############
输出
将炸弹放置在(7,11)处,最多可以消灭10个敌人。
1 #include <stdio.h> 2 char map[20][20]; 3 int n, m, book[20][20]; 4 int max=0, maxx, maxy; 5 struct node 6 { 7 int x; 8 int y; 9 }; 10 int fun(int x,int y) 11 { 12 int sum = 0, k; 13 k = x; 14 while (map[k][y] != ‘#‘&&k >= 0) 15 { 16 if (map[k][y] == ‘G‘) 17 sum++; 18 k--; 19 } 20 k = x; 21 while (map[k][y] != ‘#‘&&k < n) 22 { 23 if (map[k][y] == ‘G‘) 24 sum++; 25 k++; 26 } 27 k = y; 28 while (map[x][k] != ‘#‘&&k >= 0) 29 { 30 if (map[x][k] == ‘G‘) 31 sum++; 32 k--; 33 } 34 k = y; 35 while (map[x][k] != ‘#‘&&k <m) 36 { 37 if (map[x][k] == ‘G‘) 38 sum++; 39 k++; 40 } 41 return sum; 42 } 43 void dfs(int x,int y) 44 { 45 int next[4][2] = { {0,1},{1,0},{0,-1},{-1,0} }; 46 int i,tx,ty; 47 int sum = fun(x, y); 48 if (max < sum) 49 { 50 max = sum; 51 maxx = x; 52 maxy = y; 53 } 54 for (i = 0;i < 4;i++) 55 { 56 tx = x + next[i][0]; 57 ty = y + next[i][1]; 58 if (tx < 0 || tx >= n || ty < 0 || ty >= m) 59 continue; 60 if (map[tx][ty] == ‘.‘&&book[tx][ty] == 0) 61 { 62 book[tx][ty] = 1; 63 dfs(tx,ty); 64 } 65 } 66 return; 67 } 68 void bfs(int x,int y) 69 { 70 struct node queue[200]; 71 int head, tail,i,tx,ty,sum; 72 int next[4][2] = { {0,1},{1,0},{0,-1},{-1,0} }; 73 head = 0; 74 tail = 0; 75 queue[tail].x = x; 76 queue[tail].y = y; 77 tail++; 78 while (head < tail) 79 { 80 for (i = 0;i < 4;i++) 81 { 82 tx = queue[head].x + next[i][0]; 83 ty = queue[head].y + next[i][1]; 84 if (tx < 0 || tx >= n || ty < 0 || ty >= m) 85 continue; 86 if (map[tx][ty] == ‘.‘&&book[tx][ty] == 0) 87 { 88 queue[tail].x = tx; 89 queue[tail].y = ty; 90 tail++; 91 sum = fun(tx, ty); 92 book[tx][ty] = 1; 93 if (sum > max) 94 { 95 max = sum; 96 maxx = tx; 97 maxy = ty; 98 } 99 } 100 } 101 head++; 102 } 103 } 104 int main() 105 { 106 int i,startx,starty; 107 scanf("%d%d%d%d",&n,&m,&startx,&starty); 108 getchar(); 109 for (i = 0;i < n;i++) 110 gets(map[i]); 111 max = fun(startx,starty); 112 maxx = startx; 113 maxy = starty; 114 book[startx][starty] = 1; 115 //dfs(startx,starty); 116 bfs(startx,starty); 117 printf("max=%d,x=%d,y=%d\n",max,maxx,maxy); 118 return 0; 119 }
四、宝岛探险
问题一
小哼降落后,所在岛屿的面积大小
输入地图和降落位置(从序号1开始)
输出降落所在位置的岛屿面积
例子
输入:
10 10 6 8
1 2 1 0 0 0 0 0 2 3
3 0 2 0 1 2 1 0 1 2
4 0 1 0 1 2 3 2 0 1
3 2 0 0 0 1 2 4 0 0
0 0 0 0 0 0 1 5 3 0
0 1 2 1 0 1 5 4 3 0
0 1 2 3 1 3 6 2 1 0
0 0 3 4 8 9 7 5 0 0
0 0 0 3 7 8 6 0 1 2
0 0 0 0 0 0 0 0 1 0
输出:
38
问题二
小哼降落后,所在岛屿的面积大小
输入地图和降落位置(从序号1开始)
输出降落所在位置的岛屿
例子
输入:
10 10 6 8
1 2 1 0 0 0 0 0 2 3
3 0 2 0 1 2 1 0 1 2
4 0 1 0 1 2 3 2 0 1
3 2 0 0 0 1 2 4 0 0
0 0 0 0 0 0 1 5 3 0
0 1 2 1 0 1 5 4 3 0
0 1 2 3 1 3 6 2 1 0
0 0 3 4 8 9 7 5 0 0
0 0 0 3 7 8 6 0 1 2
0 0 0 0 0 0 0 0 1 0
输出:
1 2 1 0 0 0 0 0 2 3
3 0 2 0 -1 -1 -1 0 1 2
4 0 1 0 -1 -1 -1 -1 0 1
3 2 0 0 0 -1 -1 -1 0 0
0 0 0 0 0 0 -1 -1 -1 0
0 -1 -1 -1 0 -1 -1 -1 -1 0
0 -1 -1 -1 -1 -1 -1 -1 -1 0
0 0 -1 -1 -1 -1 -1 -1 0 0
0 0 0 -1 -1 -1 -1 0 1 2
0 0 0 0 0 0 0 0 1 0
问题三
求出地图中小岛个数
例子
输入:
10 10
1 2 1 0 0 0 0 0 2 3
3 0 2 0 1 2 1 0 1 2
4 0 1 0 1 2 3 2 0 1
3 2 0 0 0 1 2 4 0 0
0 0 0 0 0 0 1 5 3 0
0 1 2 1 0 1 5 4 3 0
0 1 2 3 1 3 6 2 1 0
0 0 3 4 8 9 7 5 0 0
0 0 0 3 7 8 6 0 1 2
0 0 0 0 0 0 0 0 1 0
输出:
-1 -1 -1 0 0 0 0 0 -2 -2
-1 0 -1 0 -3 -3 -3 0 -2 -2
-1 0 -1 0 -3 -3 -3 -3 0 -2
-1 -1 0 0 0 -3 -3 -3 0 0
0 0 0 0 0 0 -3 -3 -3 0
0 -3 -3 -3 0 -3 -3 -3 -3 0
0 -3 -3 -3 -3 -3 -3 -3 -3 0
0 0 -3 -3 -3 -3 -3 -3 0 0
0 0 0 -3 -3 -3 -3 0 -4 -4
0 0 0 0 0 0 0 0 -4 0
五、
第四章 搜索(深度、广度搜索、全排列、走迷宫、再解炸弹人、宝岛探险、水管工游戏)
声明:以上内容来自用户投稿及互联网公开渠道收集整理发布,本网站不拥有所有权,未作人工编辑处理,也不承担相关法律责任,若内容有误或涉及侵权可进行投诉: 投诉/举报 工作人员会在5个工作日内联系你,一经查实,本站将立刻删除涉嫌侵权内容。