漫步迷宫算法

1 篇文章 0 订阅
1 篇文章 0 订阅
#include <stdio.h>
#include <stdlib.h> 
# define Max 100


//数据结构...........


typedef struct
{
int row;
int col;
}Position;//迷宫中通道块的位置坐标 行,列


Position start,end;//定义全局变量表示迷宫入口和出口


typedef struct
{
int front;
int rear;
    Position Data[Max];
}Quene;




typedef struct
{
int order;//通道块在路径上的序号
Position seat;//通道块在迷宫中的坐标位置
int direction;//从此通道块到下一通道块的方向
}SElemtype;//栈的存储类型


typedef struct
{
SElemtype data[Max];
int top;
}Stack;//用栈存储当前位置


typedef struct 
{
int rownum,colnum;//迷宫的行和列
int Matrix[30][30];//迷宫数组包括外墙最大行列数目
}Maze;//迷宫




//算法............


int InitialStack(Stack *S)//初始化栈
{
(*S).top=-1;
return 1;
}


int StackEmpty(Stack S)//判断栈是否空
{
    if(S.top==-1)
return 1;
else 
return 0;
}


int StackFull(Stack S) //判断栈是否为满
{
   if (S.top==Max-1)
 return 1;
   else
 return 0;
}
void PushStack(Stack *S,SElemtype m)//入栈
{
if (!StackFull(*S)) //若栈未满 
{
(*S).top++;
(*S).data[(*S).top]=m;
}
}


void PopStack(Stack *S,SElemtype *e)//出栈
{
if (!StackEmpty(*S)) //栈不为空 
{
*e=(*S).data[(*S).top];
(*S).top--;
}
}


void InitialMaze(Maze *Mymaze)//初始化迷宫
{
(*Mymaze).rownum=(*Mymaze).colnum=0;
for (int i = 0; i <= 29; i++)
{
for (int j = 0; j <=29; j++)
{
(*Mymaze).Matrix[i][j]=0;//0表示可通,1表示不可以通行
}
}
}




void CreatMaze(Maze *Mymaze)//创建迷宫
{
int i,n,m;
    printf("创建迷宫\n");
    printf("   请输入迷宫的行和列.\n");
scanf("%d%d",&(*Mymaze).rownum,&(*Mymaze).colnum);

for (i= 0; i <= (*Mymaze).colnum + 1; i++)// 迷宫行外墙 
{
(*Mymaze).Matrix[0][i]=1;//设置为障碍墙
(*Mymaze).Matrix[(*Mymaze).rownum + 1][i]=1;
}

for (i = 0; i <= (*Mymaze).rownum + 1; i++)// 迷宫列外墙 
{
(*Mymaze).Matrix[i][0] = 1;//设置为障碍墙 
(*Mymaze).Matrix[i][(*Mymaze).colnum + 1] = 1;
}

    /*printf("  请输入迷宫不能通行的位置的个数.\n");
scanf("%d",&N);*/

for(i=1;i<(*Mymaze).rownum * (*Mymaze).colnum;i++)
{
if(i>8)
{
getchar();
system("cls");
}
        printf("   请输入迷宫的第%d个不能通行的位置的行和列(输入0,0结束).\n",i);
        scanf("%d%d",&m,&n);
if(m==0||n==0)
break;
        if (m<1 || n<1 || m > (*Mymaze).rownum || n > (*Mymaze).colnum) //越界 
        {
printf("   坐标越界,请重新输入!\n");
i--;
continue; 
        }
(*Mymaze).Matrix[m][n]=1;//表示不能通行
}
    
printf("   请设定迷宫的入口:\n");
scanf("%d%d",&start.row,&start.col);
if (start.row<1 || start.col<1 || start.row > (*Mymaze).rownum || start.col > (*Mymaze).colnum) //越界 
    {
printf("   坐标越界,请重新输入!\n");
scanf("%d%d",&start.row,&start.col);
}
    printf("   迷宫的入口为(%d,%d).\n",start.row,start.col);
    printf("\n");
printf("   请设定迷宫的出口:\n");
scanf("%d%d",&end.row,&end.col);
if (end.row<1 || end.col<1 || end.row > (*Mymaze).rownum || end.col > (*Mymaze).colnum) //越界 
    {
printf("   坐标越界,请重新输入!\n");
scanf("%d%d",&end.row,&end.col);
}  
    printf("   迷宫的出口为(%d,%d).\n",end.row,end.col); 
printf("\n");
}


int Pass(Maze Mymaze, Position seat) //判断当前位置是否可通过 
{
if (Mymaze.Matrix[seat.row][seat.col] == 0) // 可通
return 1;
else
return 0;
}


int FootPrint(Maze *Mymaze, Position seat) //标记走到当前位置可通过 
{     
(*Mymaze).Matrix[seat.row][seat.col] = 2; //2表示当前可通位置为一个路径点
return 1;
}


int NoPass(Maze *Mymaze, Position seat) // 曾走过但不是通路标记
{
(*Mymaze).Matrix[seat.row][seat.col] =3; // "3"表示曾走过但不通 
return 1;



Position NextSeat(Position *seat, int direction)  
{
switch(direction) // 1.2.3.4分别表示东,南,西,北方向 
{
case 1:
(*seat).row=(*seat).row;
(*seat).col += 1; //向东侧查找 
break;
case 2: //向南方查找 
(*seat).row += 1;
(*seat).col= (*seat).col;
break;
case 3: //向西侧查找 
(*seat).row=(*seat).row;
(*seat).col -= 1;
break;
case 4: //向北方查找 
(*seat).row -= 1;
(*seat).col=(*seat).col;
break;
default:
exit(0);
}
return *seat;
}


int MyMazePath(Maze *Mymaze,Position start,Position end)//迷宫路径
{
    Stack S;
    SElemtype e;
    InitialStack(&S);//初始化栈
int curstep=1;//路径通道块序号
Position curposition;//当前位置
    curposition.col=start.col;
curposition.row=start.row;
do
{
if(Pass(*Mymaze,curposition))
{
FootPrint(Mymaze,curposition);//标记可以走的当前位置可为迷宫路径
e.order=curstep;
e.seat.row=curposition.row;
       e.seat.col=curposition.col;
            e.direction=1;//下个位置为此点的东方向
PushStack(&S,e);


if(curposition.row==end.row&&curposition.col==end.col)
{
return 1;//查找成功
}
else//不是出口点
{
curposition=NextSeat(&curposition,e.direction);//把directio方向的下一个位置设为下一个当前位置
                curstep++;
}
}
else//当前位置为障碍点不可通
if (!StackEmpty(S))
{
PopStack(&S,&e);
                while (e.direction==4 && !StackEmpty(S)) //上一步4个方向都探测完,且栈不为空 
{
NoPass(Mymaze, e.seat); //标记该位置走过但不为通路
PopStack(&S, &e);//出栈  进while循环 
}
if (e.direction < 4) //若未探测完4个方向 
{
e.direction++; //准备探测下一个方向 
PushStack(&S, e);//将当前节点位置入栈
curposition= NextSeat(&e.seat, e.direction); //查找下一个应该探测位置的坐标 
}
}
}while(!StackEmpty(S));//栈为空时退出循环


    return 0;//栈为空时说明不能形成一条出迷宫的路径返回NULL
}


void PrintMaze(Maze Mymaze)//输出迷宫 
{
int i, j;


printf("求得的迷宫路径中各个通道块的坐标位置为:\n");
for (i = 0; i <= Mymaze.rownum + 1; i++)
{
for (j = 0; j <= Mymaze.colnum + 1; j++)
{
if ( Mymaze.Matrix[i][j]==2) //若是可通路径

printf("( %d,%d )   ",i,j);
}
}

printf("\n迷宫路径图(◎表示通路):\n");
for (i = 0; i <= Mymaze.rownum + 1; i++)
{
for (j = 0; j <= Mymaze.colnum + 1; j++)
{
if ( Mymaze.Matrix[i][j]==1) //若是不可通
printf("█");
else
if ( Mymaze.Matrix[i][j]==2) //若是可通路径 
printf("◎");
else //其他位置 
printf("  ");
}
printf("\n");
}
}
int main()
{
    Maze Mymaze;
InitialMaze(&Mymaze);
CreatMaze(&Mymaze);
if(!MyMazePath(&Mymaze,start,end))
{
printf("很抱歉!您的迷宫无法找到一条从入口到出口的合适路径!");
}
else
{
PrintMaze(Mymaze);
}
return 0;

}


//这是用深度搜索得到迷宫的一条可通路径的方法,要想得到迷宫可通最短路径就用广度搜索利用队列实现。

  • 0
    点赞
  • 2
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值