本篇文章所讲的复杂版的迷宫问题指的是在迷宫中有多条通路,程序将实现找到所有通路,并给出哪一条是最短通路。
废话不多说,直接上代码吧!!
#include <iostream>
#include <assert.h>
using namespace std;
#include <stack>
#pragma warning(disable:4996)
const size_t N = 10;
//复杂版
void InitMaze(int maze[][N], size_t N) //初始化迷宫图
{
FILE* fout = fopen("Maze.txt","r");
assert(fout);
for(size_t i=0; i<N; ++i)
{
for(size_t j=0; j<N; )
{
//获得迷宫图上坐标的ASCII值
char ch = fgetc(fout);
if((ch == '0') || (ch == '1'))
{
maze[i][j] = ch - '0';
++j;
}
}
}
}
void PrintMaze(int maze[][N], size_t N) //打印迷宫图
{
for(size_t i=0; i<N; ++i)
{
for(size_t j=0; j<N; ++j)
{
cout<<maze[i][j]<<" ";
}
cout<<endl;
}
cout<<endl;
}
struct Pos //定义位置结点
{
size_t _row; //行
size_t _col; //列
};
bool CheckAccess(int maze[][N], size_t N, Pos cur, Pos next) //判断坐标的位置是否合理
{
if(((next._row>=0) && (next._row<N)) && ((next._col>=0) && (next._col<N)))
{
if((maze[next._row][next._col] == 0)
|| (maze[next._row][next._col] > maze[cur._row][cur._col]))
{
return true;
}
}
return false;
}
bool GetMazePathR(int maze[][N], size_t N, Pos cur, stack<Pos> &ShortPath, stack<Pos> &Path)
{
Path.push(cur);
if(cur._row == N - 1)
{
if(ShortPath.empty() || (Path.size() < ShortPath.size()))
{
ShortPath = Path;
}
}
Pos next;
//上
next = cur;
next._row--;
if(CheckAccess(maze, N, cur, next))
{
maze[next._row][next._col] = maze[cur._row][cur._col] + 1;
if(GetMazePathR(maze, N, next, ShortPath, Path))
{
return true;
}
}
//右
next = cur;
next._col++;
if(CheckAccess(maze, N, cur, next))
{
maze[next._row][next._col] = maze[cur._row][cur._col] + 1;
if(GetMazePathR(maze, N, next, ShortPath, Path))
{
return true;
}
}
//下
next = cur;
next._row++;
if(CheckAccess(maze, N, cur, next))
{
maze[next._row][next._col] = maze[cur._row][cur._col] + 1;
if(GetMazePathR(maze, N, next, ShortPath, Path))
{
return true;
}
}
//左
next = cur;
next._col--;
if(CheckAccess(maze, N, cur, next))
{
maze[next._row][next._col] = maze[cur._row][cur._col] + 1;
if(GetMazePathR(maze, N, next, ShortPath, Path))
{
return true;
}
}
Path.pop();
return false;
}
void GetShortPath(int maze[][N], size_t N, Pos next)
{
stack<Pos> ShortPath;
stack<Pos> Path;
GetMazePathR(maze, N, next, ShortPath, Path);
}
void TestMaze()
{
int maze[N][N];
InitMaze(maze, N);
PrintMaze(maze, N);
stack<Pos> ShortPath;
stack<Pos> Path;
Pos entry;
entry._row = 2;
entry._col = 0;
maze[2][0] = 2;
GetShortPath(maze, N, entry);
PrintMaze(maze, N);
}
int main()
{
TestMaze();
system("pause");
return 0;
}
解决这个问题的主要方法是将探测过的坐标加1,而不是简单的赋值为2。只要稍微修改一下判断坐标合理性的条件与寻找通路的条件,很容易找到最短通路!
我们打印迷宫地图时,采用了文件的方式,如果有志同道合的人看到了这篇文章,想要动手操作一下的话,需要编写一份文本文件Maze.txt,并将它加载到项目的文件夹中。
下图为样例。