迷宫问题
来源:互联网 发布:java mysql 存储过程 编辑:程序博客网 时间:2024/05/02 04:35
迷宫问题就是典型的图的搜索问题,我们可以采用栈来实现迷宫的深度搜索,从而找到一条路径,但是却不是从入口到出口的最短路径;寻找最短搜索路径通常的方法是用广度优先搜索,利用队列来完成的。一般图的广度优先搜索算法可以简单描述为:
Void BFS(Graph G){
初始化一个队列;
从G的初始点开始;
if (当前的结点是目标结点) 搜索结束;
else 初始点进入队列;
do {
取队头结点,并产生其相邻结点;
if (产生的结点是目标结点) {输出一个解;搜索结束;}
if (产生的结点是新结点) 新结点进队列
} while (队头<=队尾);
} // end_BFS
如果我们要得到所有的解,只需找到一个解后输出,并不结束循环就可以了。我们来看一个例子。
【问题描述】
有一个迷宫,只有一个入口和一个出口,我们希望用搜索法找到一条从入口到出口的最短路径。首先应考虑怎么描述迷宫。可用二维数组mg(m,n)存储迷宫,其含义如下:
为了解决出界问题,我们在四周加上无法通过的“墙”,也就是“哨兵”,这样可以减少判断是否出界。图10-3是用二维数组表示的一个迷宫。
1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1
入口 Þ 0 0 0 0 0 0 0 0 0 0 0 0 1 0 0 0 1 0 0 0 1 1
1 1 1 1 1 1 1 1 1 1 0 1 1 1 0 1 1 1 1 1 1 1 1
1 1 0 1 0 0 0 0 0 0 0 0 0 0 0 1 0 0 0 1 0 0 1
1 1 1 1 1 1 0 1 0 1 1 1 1 1 1 1 0 1 0 1 1 1 1
1 0 0 0 0 0 0 1 0 1 0 0 0 1 0 1 0 1 0 1 0 0 1
1 1 1 1 1 1 1 1 0 1 0 1 0 1 0 1 1 1 0 1 1 1 1
1 1 0 1 0 0 0 0 0 1 0 1 0 1 0 0 0 0 0 1 0 1 1
1 1 1 1 1 1 0 1 1 1 0 1 0 1 1 1 1 1 1 1 1 1 1
1 1 0 0 0 1 0 0 0 0 0 1 0 0 0 0 0 1 0 1 0 1 1
1 1 1 1 0 1 1 1 0 1 1 1 1 1 1 1 0 1 0 1 1 1 1
1 1 0 1 0 0 0 1 0 1 0 0 0 0 0 0 0 1 0 0 0 0 1
1 1 1 1 0 1 0 1 1 1 0 1 1 1 1 1 1 1 0 1 0 1 1
1 0 0 1 0 1 0 1 0 0 0 0 0 0 0 0 0 1 0 0 0 0 1
1 1 0 1 0 1 1 1 0 1 1 1 1 1 0 1 0 1 1 1 1 1 1
1 1 0 0 0 1 0 1 0 0 0 0 0 0 0 1 0 0 0 0 0 0 Þ 出口
1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1
图10-3 迷宫的数组表示
现在来看一看搜索路径的选择:一般的迷宫可以从八个方向进行搜索,为了简化问题,我们考虑从以下四个方向去搜索:
( i-1 , j )
( i , j -1) ( i , j ) ( i , j +1)
( i+1 , j )
图 10-4 四个搜索方向
用数组表示其下标的变化(只记录其增量)如下:
1(上) 2(右) 3(下) 4(左)
行下标变化△i: -1 0 1 0
列下标变化△j: 0 1 0 -1
为了防止被搜索过的单元被重复搜索,也就是避免转圈或走重复的路径,于是应该将所走过的路径作上记号,在不增加额外的存储空间的情况下,可将mg修改如下:
为了找到最短路径,我们用队列SQueue来保存搜索过的位置。搜索的规则是:选择一个可通行的位置而又没有试探过的单元p,沿四个方向作搜索,若这四个方向中有可行通路又没有搜索过的单元q,则说明从p到q有通路,将q记录在SQueue中,SQueue[m*n]是一个三元组数组,用来记录搜索过的单元, SQueue[k].x记录第k次搜索的单元q的行坐标,SQueue[k].y记录q的列坐标,SQueue[k].pre记录产生q的单元即p单元在SQueue中的下标,即记录每个搜索单元的产生轨迹,或记录其父结点,其目的是为了在找到出口后沿这个下标返回到入口处,方便最后显示这条最短路径。这四个方向都搜索完了,(修改q单元为已搜索过);接下来从SQueue中取出对头,往下继续搜索。在搜索过程中如果遇上了出口单元,则认为已经找到了一条从入口到出口的最短路径;如果迷宫中所有可通行的道路都搜索完,都没有遇上出口单元,此时认为该迷宫是无法通过的。
【数据描述】
typedef struct{
int x,y; //搜索位置的坐标
int pre; //表示父结点的位置
}SQarray;
typedef struct{
int Deltai,Deltaj; //4个搜索方向的坐标变化值
}Direction;
int mg[m+2][n+2];
SQarray SQueue[Max];
Direction Dchange[5];
我们看看图10-3这样的迷宫,队列SQueue的变化情况:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 ...
x
1
1
1
1
1
1
1
1
1
1
1
2
1
3
...
y
1
2
3
4
5
6
7
8
9
10
11
10
12
10
...
pre
0
1
2
3
4
5
6
7
8
9
10
10
11
12
...
­ ­
front rear
图10-5 队列SQueue的变化
设入口地址是(1,1),出口地址是(m,n),我们来看一看迷宫问题的算法描述。
【算法描述】
Step1:建立迷宫数组mg[m+1][n+1];建立搜索的四个方向下标变化变量:Dchange[1..4];
Step2:给mg周围加“哨兵”;
Step3: 初始化队列:front=0;rear=0;Goout=FALSE;
Step4: 入口位置入队列SQueue:rear++;SQueue[rear].x=1;SQueue[rear].y=1;SQueue[rear].pre=0; mg[1][1]=-1;(0表示入口是第一个结点,无前驱结点);
Step5: do {
front++; i=SQueue[front].x; j=SQueue[front].y; //出队列
for (d=1;d<=4;d++){ //沿4个方向搜索
di=i+dchange[d].Deltai;dj=j+dchange[d].Deltaj; //确定新的搜索位置
if (!mg[di][dj]) { //如果新位置是未搜索通道,则将新位置入队列
rear++; SQueue[rear].x=di;SQueue[rear].y=dj;
SQueue[rear].pre=front;
Mg[di][dj]=-1; } //标识搜索过的位置为-1
if (i=m && j=n){ //找到出口
打印路径;Goout=TRUE; }
}while(front<=rear && !Goout)
Step6: if (!Goout) printf(“No Pass!/n”);
(7)若flag=0 则输出“无法走出迷宫”
【C源程序】
#include <stdio.h>
#define m 15
#define n 21
#define Max 500
typedef struct{
int x,y; /*搜索位置的坐标 */
int pre; /*表示前驱点的位置 */
}SQarray;
typedef struct{
int Deltai,Deltaj; /*4个搜索方向的坐标变化值 */
}Direction;
int mg[m+2][n+2]=
{{1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1},
{1,0,0,0,0,0,0,0,0,0,0,0,0,1,0,0,0,1,0,0,0,1,1},
{1,1,1,1,1,1,1,1,1,1,0,1,1,1,0,1,1,1,1,1,1,1,1},
{1,1,0,1,0,0,0,0,0,0,0,0,0,0,0,1,0,0,0,1,0,0,1},
{1,1,1,1,1,1,0,1,0,1,1,1,1,1,1,1,0,1,0,1,1,1,1},
{1,0,0,0,0,0,0,1,0,1,0,0,0,1,0,1,0,1,0,1,0,0,1},
{1,1,1,1,1,1,1,1,0,1,0,1,0,1,0,1,1,1,0,1,1,1,1},
{1,1,0,1,0,0,0,0,0,1,0,1,0,1,0,0,0,0,0,1,0,1,1},
{1,1,1,1,1,1,0,1,1,1,0,1,0,1,1,1,1,1,1,1,1,1,1},
{1,1,0,0,0,1,0,0,0,0,0,1,0,0,0,0,0,1,0,1,0,1,1},
{1,1,1,1,0,1,1,1,0,1,1,1,1,1,1,1,0,1,0,1,1,1,1},
{1,1,0,1,0,0,0,1,0,1,0,0,0,0,0,0,0,1,0,0,0,0,1},
{1,1,1,1,0,1,0,1,1,1,0,1,1,1,1,1,1,1,0,1,0,1,1},
{1,0,0,1,0,1,0,1,0,0,0,0,0,0,0,0,0,1,0,0,0,0,1},
{1,1,0,1,0,1,1,1,0,1,1,1,1,1,0,1,0,1,1,1,1,1,1},
{1,1,0,0,0,1,0,1,0,0,0,0,0,0,0,1,0,0,0,0,0,0,1},
{1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1}};
SQarray SQueue[Max];
Direction Dchange[5]={{0,0},{-1,0},{0,1},{1,0},{0,-1}};
void print(int k)
{int i,j,kk;
kk=k;
do
{ i=SQueue[kk].x; j=SQueue[kk].y;
mg[i][j]=3; kk=SQueue[kk].pre;
}while(kk);
printf(" 模拟迷宫路径: # 表示最后走出迷宫的路径, -1表示探索过的路径/n");
printf("进入->");
for (i=1;i<=m;i++)
{ for (j=1;j<=n;j++)
if (mg[i][j]==3) printf("%2c",'#');
else printf("%2d",mg[i][j]);
if (i==m) printf("->走出/n");
else printf("/n ");}
}
main()
{int d,i,j,di,dj,front,rear,Goout;
front=0;rear=0;Goout=0;
rear++;
SQueue[rear].x=1;SQueue[rear].y=1;SQueue[rear].pre=0; mg[1][1]=-1;
do {
front++; i=SQueue[front].x; j=SQueue[front].y; /*出队列 */
for (d=1;d<=4;d++){ /*沿4个方向搜索*/
di=i+Dchange[d].Deltai; dj=j+Dchange[d].Deltaj; /*确定新的搜索位置 */
if (!mg[di][dj]) { /*如果新位置是未搜索通道,则将新位置入队列*/
rear++; SQueue[rear].x=di;SQueue[rear].y=dj;
SQueue[rear].pre=front;
mg[di][dj]=-1; } /*标识搜索过的位置为-1 */
if (i==m && j==n){ /*找到出口*/
print(rear); Goout=1; }
}
}while(front<=rear && !Goout);
if (!Goout) printf("No Pass!/n");
}
【运行结果】
模拟迷宫路径: # 表示最后走出迷宫的路径, -1表示探索过的路径
进入 –> # # # # # # # # # # -1 -1 1 -1 -1 -1 1 0 0 0 1
1 1 1 1 1 1 1 1 1 # 1 1 1 -1 1 1 1 1 1 1 1
1 0 1 -1 -1 -1 -1 # # # -1 -1 -1 -1 1 0 0 0 1 0 0
1 1 1 1 1 -1 1 # 1 1 1 1 1 1 1 0 1 0 1 1 1
-1 -1 -1 -1 -1 -1 1 # 1 # # # 1 0 1 0 1 0 1 0 0
1 1 1 1 1 1 1 # 1 # 1 # 1 0 1 1 1 0 1 1 1
1 0 1 -1 -1 # # # 1 # 1 # 1 0 0 0 0 0 1 0 1
1 1 1 1 1 # 1 1 1 # 1 # 1 1 1 1 1 1 1 1 1
1 0 0 0 1 # # # # # 1 # # # # # 1 0 1 0 1
1 1 1 0 1 1 1 -1 1 1 1 1 1 1 1 # 1 0 1 1 1
1 0 1 0 0 0 1 -1 1 # # # # # # # 1 0 0 0 0
1 1 1 0 1 0 1 1 1 # 1 1 1 1 1 1 1 0 1 0 1
0 0 1 0 1 0 1 -1 -1 # # # # # # # 1 0 0 0 0
1 0 1 0 1 1 1 -1 1 1 1 1 1 -1 1 # 1 1 1 1 1
1 0 0 0 1 0 1 -1 -1 -1 -1 -1 -1 -1 1 # # # # # # -> 走出
【说明】算法的时间复杂度取决于搜索单元的个数,即数组SQueue的使用大小,最坏的情况是 。
【实验题】
1. 将上题迷宫的4个搜索方向改成8个搜索方向,看看运行的结果怎样;
2. 改进上面的程序,求出所有的通路,并统计从迷宫的入口到出口共有几条通路;
3. 将队列改成栈来解决迷宫问题,并比较这两种方法的差异。
Void BFS(Graph G){
初始化一个队列;
从G的初始点开始;
if (当前的结点是目标结点) 搜索结束;
else 初始点进入队列;
do {
取队头结点,并产生其相邻结点;
if (产生的结点是目标结点) {输出一个解;搜索结束;}
if (产生的结点是新结点) 新结点进队列
} while (队头<=队尾);
} // end_BFS
如果我们要得到所有的解,只需找到一个解后输出,并不结束循环就可以了。我们来看一个例子。
【问题描述】
有一个迷宫,只有一个入口和一个出口,我们希望用搜索法找到一条从入口到出口的最短路径。首先应考虑怎么描述迷宫。可用二维数组mg(m,n)存储迷宫,其含义如下:
为了解决出界问题,我们在四周加上无法通过的“墙”,也就是“哨兵”,这样可以减少判断是否出界。图10-3是用二维数组表示的一个迷宫。
1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1
入口 Þ 0 0 0 0 0 0 0 0 0 0 0 0 1 0 0 0 1 0 0 0 1 1
1 1 1 1 1 1 1 1 1 1 0 1 1 1 0 1 1 1 1 1 1 1 1
1 1 0 1 0 0 0 0 0 0 0 0 0 0 0 1 0 0 0 1 0 0 1
1 1 1 1 1 1 0 1 0 1 1 1 1 1 1 1 0 1 0 1 1 1 1
1 0 0 0 0 0 0 1 0 1 0 0 0 1 0 1 0 1 0 1 0 0 1
1 1 1 1 1 1 1 1 0 1 0 1 0 1 0 1 1 1 0 1 1 1 1
1 1 0 1 0 0 0 0 0 1 0 1 0 1 0 0 0 0 0 1 0 1 1
1 1 1 1 1 1 0 1 1 1 0 1 0 1 1 1 1 1 1 1 1 1 1
1 1 0 0 0 1 0 0 0 0 0 1 0 0 0 0 0 1 0 1 0 1 1
1 1 1 1 0 1 1 1 0 1 1 1 1 1 1 1 0 1 0 1 1 1 1
1 1 0 1 0 0 0 1 0 1 0 0 0 0 0 0 0 1 0 0 0 0 1
1 1 1 1 0 1 0 1 1 1 0 1 1 1 1 1 1 1 0 1 0 1 1
1 0 0 1 0 1 0 1 0 0 0 0 0 0 0 0 0 1 0 0 0 0 1
1 1 0 1 0 1 1 1 0 1 1 1 1 1 0 1 0 1 1 1 1 1 1
1 1 0 0 0 1 0 1 0 0 0 0 0 0 0 1 0 0 0 0 0 0 Þ 出口
1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1
图10-3 迷宫的数组表示
现在来看一看搜索路径的选择:一般的迷宫可以从八个方向进行搜索,为了简化问题,我们考虑从以下四个方向去搜索:
( i-1 , j )
( i , j -1) ( i , j ) ( i , j +1)
( i+1 , j )
图 10-4 四个搜索方向
用数组表示其下标的变化(只记录其增量)如下:
1(上) 2(右) 3(下) 4(左)
行下标变化△i: -1 0 1 0
列下标变化△j: 0 1 0 -1
为了防止被搜索过的单元被重复搜索,也就是避免转圈或走重复的路径,于是应该将所走过的路径作上记号,在不增加额外的存储空间的情况下,可将mg修改如下:
为了找到最短路径,我们用队列SQueue来保存搜索过的位置。搜索的规则是:选择一个可通行的位置而又没有试探过的单元p,沿四个方向作搜索,若这四个方向中有可行通路又没有搜索过的单元q,则说明从p到q有通路,将q记录在SQueue中,SQueue[m*n]是一个三元组数组,用来记录搜索过的单元, SQueue[k].x记录第k次搜索的单元q的行坐标,SQueue[k].y记录q的列坐标,SQueue[k].pre记录产生q的单元即p单元在SQueue中的下标,即记录每个搜索单元的产生轨迹,或记录其父结点,其目的是为了在找到出口后沿这个下标返回到入口处,方便最后显示这条最短路径。这四个方向都搜索完了,(修改q单元为已搜索过);接下来从SQueue中取出对头,往下继续搜索。在搜索过程中如果遇上了出口单元,则认为已经找到了一条从入口到出口的最短路径;如果迷宫中所有可通行的道路都搜索完,都没有遇上出口单元,此时认为该迷宫是无法通过的。
【数据描述】
typedef struct{
int x,y; //搜索位置的坐标
int pre; //表示父结点的位置
}SQarray;
typedef struct{
int Deltai,Deltaj; //4个搜索方向的坐标变化值
}Direction;
int mg[m+2][n+2];
SQarray SQueue[Max];
Direction Dchange[5];
我们看看图10-3这样的迷宫,队列SQueue的变化情况:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 ...
x
1
1
1
1
1
1
1
1
1
1
1
2
1
3
...
y
1
2
3
4
5
6
7
8
9
10
11
10
12
10
...
pre
0
1
2
3
4
5
6
7
8
9
10
10
11
12
...
­ ­
front rear
图10-5 队列SQueue的变化
设入口地址是(1,1),出口地址是(m,n),我们来看一看迷宫问题的算法描述。
【算法描述】
Step1:建立迷宫数组mg[m+1][n+1];建立搜索的四个方向下标变化变量:Dchange[1..4];
Step2:给mg周围加“哨兵”;
Step3: 初始化队列:front=0;rear=0;Goout=FALSE;
Step4: 入口位置入队列SQueue:rear++;SQueue[rear].x=1;SQueue[rear].y=1;SQueue[rear].pre=0; mg[1][1]=-1;(0表示入口是第一个结点,无前驱结点);
Step5: do {
front++; i=SQueue[front].x; j=SQueue[front].y; //出队列
for (d=1;d<=4;d++){ //沿4个方向搜索
di=i+dchange[d].Deltai;dj=j+dchange[d].Deltaj; //确定新的搜索位置
if (!mg[di][dj]) { //如果新位置是未搜索通道,则将新位置入队列
rear++; SQueue[rear].x=di;SQueue[rear].y=dj;
SQueue[rear].pre=front;
Mg[di][dj]=-1; } //标识搜索过的位置为-1
if (i=m && j=n){ //找到出口
打印路径;Goout=TRUE; }
}while(front<=rear && !Goout)
Step6: if (!Goout) printf(“No Pass!/n”);
(7)若flag=0 则输出“无法走出迷宫”
【C源程序】
#include <stdio.h>
#define m 15
#define n 21
#define Max 500
typedef struct{
int x,y; /*搜索位置的坐标 */
int pre; /*表示前驱点的位置 */
}SQarray;
typedef struct{
int Deltai,Deltaj; /*4个搜索方向的坐标变化值 */
}Direction;
int mg[m+2][n+2]=
{{1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1},
{1,0,0,0,0,0,0,0,0,0,0,0,0,1,0,0,0,1,0,0,0,1,1},
{1,1,1,1,1,1,1,1,1,1,0,1,1,1,0,1,1,1,1,1,1,1,1},
{1,1,0,1,0,0,0,0,0,0,0,0,0,0,0,1,0,0,0,1,0,0,1},
{1,1,1,1,1,1,0,1,0,1,1,1,1,1,1,1,0,1,0,1,1,1,1},
{1,0,0,0,0,0,0,1,0,1,0,0,0,1,0,1,0,1,0,1,0,0,1},
{1,1,1,1,1,1,1,1,0,1,0,1,0,1,0,1,1,1,0,1,1,1,1},
{1,1,0,1,0,0,0,0,0,1,0,1,0,1,0,0,0,0,0,1,0,1,1},
{1,1,1,1,1,1,0,1,1,1,0,1,0,1,1,1,1,1,1,1,1,1,1},
{1,1,0,0,0,1,0,0,0,0,0,1,0,0,0,0,0,1,0,1,0,1,1},
{1,1,1,1,0,1,1,1,0,1,1,1,1,1,1,1,0,1,0,1,1,1,1},
{1,1,0,1,0,0,0,1,0,1,0,0,0,0,0,0,0,1,0,0,0,0,1},
{1,1,1,1,0,1,0,1,1,1,0,1,1,1,1,1,1,1,0,1,0,1,1},
{1,0,0,1,0,1,0,1,0,0,0,0,0,0,0,0,0,1,0,0,0,0,1},
{1,1,0,1,0,1,1,1,0,1,1,1,1,1,0,1,0,1,1,1,1,1,1},
{1,1,0,0,0,1,0,1,0,0,0,0,0,0,0,1,0,0,0,0,0,0,1},
{1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1}};
SQarray SQueue[Max];
Direction Dchange[5]={{0,0},{-1,0},{0,1},{1,0},{0,-1}};
void print(int k)
{int i,j,kk;
kk=k;
do
{ i=SQueue[kk].x; j=SQueue[kk].y;
mg[i][j]=3; kk=SQueue[kk].pre;
}while(kk);
printf(" 模拟迷宫路径: # 表示最后走出迷宫的路径, -1表示探索过的路径/n");
printf("进入->");
for (i=1;i<=m;i++)
{ for (j=1;j<=n;j++)
if (mg[i][j]==3) printf("%2c",'#');
else printf("%2d",mg[i][j]);
if (i==m) printf("->走出/n");
else printf("/n ");}
}
main()
{int d,i,j,di,dj,front,rear,Goout;
front=0;rear=0;Goout=0;
rear++;
SQueue[rear].x=1;SQueue[rear].y=1;SQueue[rear].pre=0; mg[1][1]=-1;
do {
front++; i=SQueue[front].x; j=SQueue[front].y; /*出队列 */
for (d=1;d<=4;d++){ /*沿4个方向搜索*/
di=i+Dchange[d].Deltai; dj=j+Dchange[d].Deltaj; /*确定新的搜索位置 */
if (!mg[di][dj]) { /*如果新位置是未搜索通道,则将新位置入队列*/
rear++; SQueue[rear].x=di;SQueue[rear].y=dj;
SQueue[rear].pre=front;
mg[di][dj]=-1; } /*标识搜索过的位置为-1 */
if (i==m && j==n){ /*找到出口*/
print(rear); Goout=1; }
}
}while(front<=rear && !Goout);
if (!Goout) printf("No Pass!/n");
}
【运行结果】
模拟迷宫路径: # 表示最后走出迷宫的路径, -1表示探索过的路径
进入 –> # # # # # # # # # # -1 -1 1 -1 -1 -1 1 0 0 0 1
1 1 1 1 1 1 1 1 1 # 1 1 1 -1 1 1 1 1 1 1 1
1 0 1 -1 -1 -1 -1 # # # -1 -1 -1 -1 1 0 0 0 1 0 0
1 1 1 1 1 -1 1 # 1 1 1 1 1 1 1 0 1 0 1 1 1
-1 -1 -1 -1 -1 -1 1 # 1 # # # 1 0 1 0 1 0 1 0 0
1 1 1 1 1 1 1 # 1 # 1 # 1 0 1 1 1 0 1 1 1
1 0 1 -1 -1 # # # 1 # 1 # 1 0 0 0 0 0 1 0 1
1 1 1 1 1 # 1 1 1 # 1 # 1 1 1 1 1 1 1 1 1
1 0 0 0 1 # # # # # 1 # # # # # 1 0 1 0 1
1 1 1 0 1 1 1 -1 1 1 1 1 1 1 1 # 1 0 1 1 1
1 0 1 0 0 0 1 -1 1 # # # # # # # 1 0 0 0 0
1 1 1 0 1 0 1 1 1 # 1 1 1 1 1 1 1 0 1 0 1
0 0 1 0 1 0 1 -1 -1 # # # # # # # 1 0 0 0 0
1 0 1 0 1 1 1 -1 1 1 1 1 1 -1 1 # 1 1 1 1 1
1 0 0 0 1 0 1 -1 -1 -1 -1 -1 -1 -1 1 # # # # # # -> 走出
【说明】算法的时间复杂度取决于搜索单元的个数,即数组SQueue的使用大小,最坏的情况是 。
【实验题】
1. 将上题迷宫的4个搜索方向改成8个搜索方向,看看运行的结果怎样;
2. 改进上面的程序,求出所有的通路,并统计从迷宫的入口到出口共有几条通路;
3. 将队列改成栈来解决迷宫问题,并比较这两种方法的差异。