数据结构作业——走迷宫

算法思想:采用“回溯法”,利用堆栈,保存所有可能路径每一点的下标和从该点前进的方向。
  从入口出发,往正东走,若能走通(到达未走过的点),则从新点继续走,否则回到之前的点换个方向走。
代码下载:https://github.com/liuzhaoze/DataStructureHomework

代码

#include <stdio.h>
#include <stdlib.h>

#define m 6  //迷宫实际行数
#define n 8  //迷宫实际列数
#define N (m * n)

//"1"表示迷宫的墙,"0"表示迷宫可走的路,"2"表示已经走过的路
//n+3是为了给'\0'留位置
char maze[m+2][n+3] = {
    "1111111111",
    "1011101101",
    "1101010101",
    "1010110011",
    "1011011011",
    "1100110001",
    "1011101101",
    "1111111111"
};

//声明移动方向结构体
struct Move {int x; int y;};
//定义八个移动方向
struct Move Dir[8] = {
    {0,  1}, { 1,  1}, {1,  0}, { 1, -1},//正东,东南,正南,西南
    {0, -1}, {-1, -1}, {-1, 0}, {-1,  1} //正西,西北,正北,东北
};

//声明位置信息结构体,(x, y)表示当前所处位置,dir表示将要去但还没去的方向
struct Location
{
    int x;
    int y;
    int dir;
};
//定义一个以位置信息为元素的栈
struct Location Stack[N];
int top = 0;//定义栈顶
//以下是与堆栈有关的函数
void Push(struct Location t)//入栈
{
    if(top == N)
    {
        printf("Stack overflow!\n");
        exit(-2);//上溢
    }
    Stack[top++] = t;
}

struct Location Pop(void)//出栈
{
    if(top == 0)
    {
        printf("Stack underflow!\n");
        exit(-3);//下溢
    }
    return Stack[--top];
}

int StackIsEmpty(void)//判断栈是否为空
{
    return top == 0;
}

//主函数
int main()
{
    struct Location ToWalk = {1, 1, 0}, next;
    Push(ToWalk);
    //注:压入栈的是要走但还没走的步
    while(!StackIsEmpty())
    {
        ToWalk = Pop();//从栈顶弹出要走的步的信息

        if(ToWalk.dir == 0)//dir=0说明是第一次走这个位置,需要将0置2
        {
            if(maze[ToWalk.x][ToWalk.y] != '0')//要走的位置是墙或者已经走过
                continue;//跳过本次循环
            maze[ToWalk.x][ToWalk.y] = '2';//将0置2,标记已经来到此位置
            if(ToWalk.x == m && ToWalk.y == n)//已经走到迷宫的出口
                exit(0);//0表示走出去了,1表示没走出去
        }

        //来到此位置之后,配置下一个要走的步的参数
        next.x = ToWalk.x + Dir[ToWalk.dir].x;
        next.y = ToWalk.y + Dir[ToWalk.dir].y;
        next.dir = 0;

        if(++ToWalk.dir < 8)//在这个位置的八个方向没有全部尝试完
            Push(ToWalk);//将 当回到该位置时,下一次应该尝试的方向 压入栈中

        Push(next);//把下一步的参数压入栈中
    }

    //栈空代表所有可能都尝试了
    printf("No Path.\n");

    return 1;//0表示走出去了,1表示没走出去
}
  • 2
    点赞
  • 13
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值