。。。

导航

codeup 1742: 算法3-3:迷宫

题目描述
有一个 10 x 10 的迷宫,起点是‘S’,终点是‘E’,墙是‘#’,道路是空格。一个机器人从起点走到终点。当机器人走到一个通道块,前面已经没有路可走时,它会转向到当前面向的右手方向继续走。如果机器人能够过,则留下足迹‘*’,如果走不通,则留下标记‘!’。
下面给出书中的算法,请你模拟机器人的走法输出最终的状态。
这里写图片描述
图:迷宫算法
输入
一个 10 x 10 的二维字符数组。

输出
机器人走过的路径状态。

样例输入

##########
#S #   # #
#  #   # #
#    ##  #
# ###    #
#   #    #
# #   #  #
# ### ## #
##      E#
##########
样例输出
##########
#**#!!!# #
# *#!!!# #
#**!!##  #
#*###    #
#***#    #
# #***#  #
# ###*## #
##   ****#
##########

注意点:

  • —方向是顺时针进行探索
  • — 在s->top++中,用括号(s->top)++,优先级的问题,已经被这个点坑了两次了
    其余没什么好说的,具体的步骤已经写在注释里
#include<stdio.h>
#include<stdlib.h>

#define N 10
#define STACK_INIT_SIZE 100
#define STACKINCREMENT 10
#define ERROR 0
#define OK 1
char maze[N+10][N+10];
typedef int Status;
typedef struct{
    int x;
    int y;
}PosType;

typedef struct{
    int ord;//步数 
    PosType seat;//坐标位置 
    int di;//方向 
}SElemType;

typedef struct {
    SElemType *base;
    SElemType *top;
    int stacksize;  
}SqStack; 

Status InitStack(SqStack *s)
{//初始化栈 
    s->base = (SElemType*)malloc(STACK_INIT_SIZE*sizeof(SElemType));
    if(!s->base )
        return ERROR;
    s->top = s->base ;
    s->stacksize =  STACK_INIT_SIZE;
    return OK; 
}

Status Pass(char maze[][N+10],PosType *s)
{//判断是否可以通过 

    if(maze[s->x][s->y]==' '||maze[s->x][s->y]=='S'||maze[s->x][s->y] == 'E')
        return OK;
    else
        return ERROR;
}

void FootPrint(char maze[][N+10],PosType *s)
{//留下能够通过的标记 
    maze[s->x ][s->y ] = '*';
}

Status Push(SqStack *s,SElemType *e)
{//入栈 
    SElemType *newbase;
    if( (s->top-s->base )>= s->stacksize )
    {
        newbase = (SElemType*)realloc(s->base,(s->stacksize+STACKINCREMENT)*sizeof(SElemType));
        if(!newbase)
            return ERROR;
        s->base = newbase;
        s->stacksize += STACKINCREMENT;
    }
    *(s->top)++= *e;

    return OK;
} 

Status Pop(SqStack *s,SElemType *e)
{//出栈 
    if(s->base == s->top )
        return ERROR;
    *e = *--(s->top);
    return OK;
}

PosType NextPose(PosType *s,int i)
{//更新位置 
    if(i == 1)
        s->y = s->y +1;
    else if(i == 2)
        s->x = s->x +1;
    else if( i == 3)
        s->y = s->y -1;
    else
        s->x = s->x -1;
    return *s;
} 

Status EmptyStack(SqStack *s)
{//判断是否为空 
    if(s->base == s->top )
        return OK;
    return ERROR;
}

void MarkPrint(char maze[][N+10],PosType *s)
{
    maze[s->x ][s->y] = '!';
 } 
Status MazePath(char maze[][N+10],PosType start,PosType end)
{
    //算法3.3
    //若迷宫maze中存在从入口start到出口end的通道,则求得一条存放在栈中,并返回OK ,否则返回ERROR 
    SqStack s;
    InitStack(&s);
    PosType curpos = start;//设定当前位置为入口位置 
    SElemType e;
    int curstep = 1;//探索第一步 
    do{
        if(Pass(maze,&curpos))//当前位置可以通过 
        {
            FootPrint(maze,&curpos);//留下足迹 
            e.di = 1;
            e.ord = curstep;
            e.seat = curpos;
            Push(&s,&e);//加入路径 
            if(curpos.x == end.x &&curpos.y == end.y )
            {
                return OK;//到达终点 
            }

            curpos = NextPose(&curpos,e.di );//下一个位置是当前位置的东邻 
        curstep ++;//探索下一步 
        }
        else
        {//当前位置不能通过 

            if(!EmptyStack(&s))
            {
                Pop(&s,&e);
                while(e.di == 4&&!EmptyStack(&s))
                {
                    MarkPrint(maze,&e.seat);//留下不能通过的标记 
                    Pop(&s,&e);//退回一步 
                }
                if(e.di < 4)
                {
                    e.di ++;
                    Push(&s,&e);//换下一个方向 
                    curpos = NextPose(&e.seat,e.di);//当前位置为新方向的相邻块 
                }
            }
        }
    }while(!EmptyStack(&s));
}

int main()
{
    int i,j;
    PosType start,end;
    for( i = 0; i < 10; i ++)
    {
        for( j = 0; j <10; j ++)
        {
            scanf("%c",&maze[i][j]);
            if(maze[i][j] == 'S')
            {
                start.x = i;
                start.y = j;
            }
            if(maze[i][j] == 'E')
            {
                end.x = i;
                end.y = j;
            }
        }
        getchar();
    }

    if(MazePath(maze,start,end))
    {
        for( i = 0; i < 10; i ++)
        {
           for( j = 0; j <10; j ++)
                printf("%c",maze[i][j]);
            printf("\n");
        }

    }

    return 0;
 } 

posted on 2017-06-30 13:22  大学僧  阅读(320)  评论(0编辑  收藏  举报