栈的应用之迷宫问题

来源:互联网 发布:算法引论 pdf百度云 编辑:程序博客网 时间:2024/04/29 19:34

走迷宫的规则:

当前坐标是(i, j)下一步可以往四个方向行走,上下左右。在迷宫数组 0标识可以走,1标识不能走 2 标记已经走过 3标识回退的路

穷举法走出迷宫有两种方法:

方法一:用栈模拟

具体思路:

当遇到地图的位置为0时,表示此位置可以透过,将其位置的值由0变为i,并进行压栈处理,将此位置保存,以便此路径不通时进行回溯。假如某位置的上下左右都不通时,将此位置标记为3(表示已经走过此位置),并进行弹出操作。假如到了边界位置,则表示走出迷宫。若回溯到了迷宫的入口,则表示迷宫没有出口。

代码如下:

struct Pos{int _row;int _col;};void GetMaze(int* a, int n){assert(a);FILE* fout = fopen("MazeMap.txt", "r");assert(fout);for (int i = 0; i < n; ++i){for (int j = 0; j < n; ){char ch = fgetc(fout);if (ch == '1' || ch == '0'){a[i*n + j] = ch - '0';++j;}}}}void PrintMaze(int* a, int n){for (int i = 0; i < n; ++i){for (int j = 0; j < n; ++j){cout << a[i*n + j]<<" ";}cout << endl;}cout << endl;}bool CheckIsAccess(int* a, int n, const Pos& next){int  row = next._row;int col = next._col;if (row >= 0 && row < n&&col >= 0 && col < n&&a[row*n + col] == 0){return true;}else{return false;}}bool SearchMazeSize(int* a, int n, Pos entry, stack<Pos>& paths){assert(a);//Pos cur = entry;paths.push(entry);while (!paths.empty()){Pos cur = paths.top();a[cur._row*n + cur._col] = 2;if (cur._row == n - 1){return true;}Pos next = cur;//上next._row--;if (CheckIsAccess(a, n, next)){paths.push(next);continue;}//下next = cur;next._row++;if (CheckIsAccess(a, n, next)){paths.push(next);continue;}//左next = cur;next._col--;if (CheckIsAccess(a, n, next)){paths.push(next);continue;}//右next = cur;next._col++;if (CheckIsAccess(a, n, next)){paths.push(next);continue;}a[cur._row*n + cur._col] = 3;paths.pop();}return false;}

测试用例:

void Test1(){int a[N][N] = { 0 };GetMaze((int*)a, N);cout << "迷宫:" << endl;PrintMaze((int*)a, N);stack<Pos> paths;Pos entry = { 2,0 };//入口坐标cout << "是否有通路?" << SearchMazeSize((int*)a, N, entry, paths) << endl;cout << endl;PrintMaze((int*)a, N);}
运行结果:




0 0