1 /** 2 通过一个题目来认识深度优先搜索 3 题目描述: 4 一个N*M迷宫,入口S,出口D,能走的是.,不能走的是X,问从入口进入后能否在T时间内走出迷宫? 5 6 输入: 7 N,M,T分别代表迷宫的长度和宽度以及时间,注意三者输入都是0时,结束 8 9 输出: 10 能走出为YES;不能走出为NO 11 12 样例输入: 13 4 4 5 14 S.X. 15 ..X. 16 ..XD 17 .... 18 3 4 5 19 S.X. 20 ..X. 21 ...D 22 0 0 0 23 24 样例输出: 25 NO 26 YES 27 代码用VS2012有点儿小问题哈~*/ 28 29 #include<cstdio> 30 #include<cstdlib> 31 using namespace std; 32 33 char maze[101][101];//保存地图信息 34 int n, m ,t;//地图大小为n * m,从起点到终点能否恰为t秒 35 bool success;//是否找到所需状态标记 36 int go[][2] = {1, 0, -1, 0, 0, 1, 0, -1};//四方向行走坐标差 37 38 //递归形式的深度优先搜索 39 void DFS(int x, int y, int time) 40 { 41 //枚举四个相邻位置 42 for(int i = 0 ; i < 4 ; i ++) 43 { 44 //nx表示上下坐标,ny表示左右坐标,其实是一样的~~ 45 int nx = x + go[i][0]; 46 int ny = y + go[i][1];//计算其坐标 47 48 if(nx < 1 || nx > n || ny < 1 || ny > m)//超出界限 49 continue; 50 51 if(maze[nx][ny] == 'X')//路障 52 continue ; 53 if(maze[nx][ny] == 'D')//出口 54 { 55 if(time + 1 == t)//再走一步,时间恰好为t,皆大欢喜 56 { 57 success = true; 58 return ; 59 } 60 else 61 continue; 62 } 63 maze[nx][ny] = 'X';//将走过的格子设为路障 64 65 DFS(nx, ny, time +1);//递归进行下一次搜索 66 maze[nx][ny] = '.';//若其后状态全部搜索完毕,则退回上层状态,将因为搜索其后续状态改成路障的位置改为普通位置 67 68 if(success) 69 return ; 70 } 71 } 72 73 int main() 74 { 75 while(scanf_s("%d%d%d", &n, &m, &t) != EOF) 76 { 77 if( n ==0 && m == 0 && t ==0) 78 break; 79 getchar(); 80 for(int i = 1 ; i <= n ; i ++) 81 { 82 gets_s(maze[i] + 1, m); 83 }//输入 84 85 success = false;//初始化成功标记 86 87 //找到出口 88 int sx, sy; 89 for(int i = 1 ; i <= n ; i ++) 90 { 91 for(int j = 1 ; j <= m ; j ++) 92 { 93 if(maze[i][j] == 'D') 94 { 95 sx = i; 96 sy = j; 97 } 98 } 99 } 100 for(int i = 1 ; i <= n ; i ++) 101 { 102 for(int j = 1 ; j <= m ; j ++) 103 { 104 //找到S点后,先判断S与D的就关系,是否符合t,不符合的话直接跳过搜索 105 if(maze[i][j] == 'S' && (i + j) % 2 == ((sx + sy) % 2 + t % 2) % 2 ) 106 { 107 maze[i][j] = 'X'; 108 DFS(i, j, 0); 109 } 110 } 111 } 112 113 puts(success == true ? "YES" : "NO");//输出结果 114 } 115 116 return 0; 117 }