回 帖 发 新 帖 刷新版面

主题:编程就+分(1期)!!!

1.迷宫问题
问题描述: 
以一个m*n 的长方阵表示迷宫,0和1分别表示迷宫中的通路和障碍。设计一个程序,对任意设定的迷宫,求出一条从入口的通道,或得出没有通路的结论。 
迷宫数据从文件中读取出来
迷宫输入文件: 
9 8 
0 0 1 0 0 0 1 0 
0 0 1 0 0 0 1 0 
0 0 0 0 1 1 0 1 
0 1 1 1 0 0 1 0 
0 0 0 1 0 0 0 0 
0 1 0 0 0 1 0 1
0 1 1 1 1 0 0 1 
1 1 0 0 0 1 0 1 
1 1 0 0 0 0 0 0 




回复列表 (共22个回复)

11 楼

闷!
典型的回朔
用一个二维数组来保存迷宫,先加一圈墙防止出界,然后在从(1,1)开始走,每探测到上下左右有一个通路就走一步并保存,为防止绕圈可用一个数组来加以判断,直到走到右下角(通路)或退出回朔(死路).剩下的信息我就不写了.....

12 楼


我说话算数!!

Program puzzle;
  const maxn=20;
  type
     ptype=array[1..maxn,1..maxn]of 0..1;
     atype=array[1..4,1..2]of -1..1;
     btype=array[1..sqr(maxn)]of integer;
  const
       a:atype=((-1,0),(0,1),(1,0),(0,-1));
  var
     puzz:ptype;
     b:btype;
     m,n,p,q,p1,q1,k,i,mn:integer;
     o:boolean;
  procedure init;
    var
       i,j:integer;
       x:0..1;
    begin
       readln(m,n);
       for i:=1 to m do
         begin
           for j:=1 to n do
             begin
               read(x);
               puzz[i,j]:=x;
             end;
           readln;
         end;
       if (m=1)and(n=1)then begin
         writeln('(1,1)');halt;
         end;
    end;
  procedure print;
    var
       i,p,q:integer;
    begin
       p:=1;q:=1;i:=2;
       write('(',1,',',1,')');
       while b[i]<>0 do
         begin
           p:=p+a[b[i],1];
           q:=q+a[b[i],2];
           inc(i);
           write(' --> (',p,',',q,')');
         end;
    end;
  procedure work;
    begin
     init;
     b[1]:=0;
     p:=1;q:=1;i:=2;
     mn:=m*n;
     k:=0;
     repeat
       repeat
         inc(k);
         o:=true;
         p1:=p+a[k,1];
         q1:=q+a[k,2];
         if (p1<=0)or(p1>m)or(q1<=0)or(q1>n)or(puzz[p1,q1]=1) then o:=false;
       until(k=4)or(o);
       if o then begin
         b[i]:=k;
         inc(i);
         puzz[p1,q1]:=1;
         p:=p1;q:=q1;
         k:=0;
          end
            else begin
              repeat
                dec(i);
                k:=b[i];
                puzz[p,q]:=0;
                p:=p-a[k,1];
                q:=q-a[k,2];
              until k<>4;
                 end;
       bb:=false;
       bbb:=false;
       bbbb:=false;
     until ((p=m) and (q=n))or i=1;
    end;
  begin
     work;
     if i=1 then writeln('no solution!')
       else print;
end.
[em9]

13 楼

别说风凉话!!!

14 楼


puzz是迷宫,为了避免兜圈子,我把走过的格子都记为1,也就是墙壁,这样避免了死循环。。。
其他的就是典型的回溯啦!!

楼主,给分!!!

15 楼

同意

16 楼


对了,我还有一个疑问:走迷宫的时候可不可以斜着走?就是比如说:
0 1 1
1 0 1
1 1 0
这样的迷宫,算可以走通的吗??如果是的话,那我的程序就要改一改了。
你给我答复,然后我去修改![em11][em11]

17 楼

走不通!

18 楼

应该不行吧
根据题目的图来说...

19 楼

/*This is the program of mazepath*/
#include <time.h>
#include <stdio.h>
#include <math.h>
#include <conio.h>
#define ENTER 2
#define EXIT 3
#define OBTACLE 0
#define PATH 1
#define FOOTPRINT -5
#define MAX 100
#define BOOLEAN int
#define TRUE 1
#define FALSE 0
#define DIRECTION int
#define NODIR 0
#define EAST 1
#define SOUTH 2
#define WEST 3
#define NORTH 4
#define RESPATH -10
typedef struct
{
    int top;
    int base;
    int Err;
    int stackX[1000];
    int stackY[1000];
    DIRECTION stackDir[1000];
}STACK;
void mazePro(int (*maze)[MAX],int m,int n);
BOOLEAN mazePath(int (*maze)[MAX],int m,int n);
void Initialize(STACK *varstack);
BOOLEAN judgeStack(STACK varstack,int X,int Y);
BOOLEAN nextDir(int *X,int *Y,DIRECTION nowdir);
int main(void)
{
    int maze[MAX][MAX];
    int X_input,Y_input;
    BOOLEAN flag;
    printf("Please input X:(not more than 99)");
    scanf("%d",&X_input);
    getchar();
    printf("Please input Y:(not more than 99)");
    scanf("%d",&Y_input);
    getchar();
    /*输入结束*/
    mazePro(maze,X_input,Y_input);
    system("pause");
    system("cls");
    flag=mazePath(maze,X_input,Y_input);
    if(flag==TRUE) printf("SUCCESS!\n");
    else printf("No Way!\n");
    getch();
    return 0;
}     
void mazePro(int (*maze)[MAX],int m,int n)
{
     int mazepos_X,mazepos_Y;
     time_t vartime;
     for(mazepos_Y=0;mazepos_Y<m;mazepos_Y++) maze[0][mazepos_Y]=maze[n-1][mazepos_Y]=OBTACLE;
     for(mazepos_X=0;mazepos_X<n;mazepos_X++) maze[mazepos_X][0]=maze[mazepos_X][m-1]=OBTACLE;
     srand((unsigned)time(&vartime));
     for(mazepos_X=1;mazepos_X<n-1;mazepos_X++)
     {
         for(mazepos_Y=1;mazepos_Y<m-1;mazepos_Y++)
             maze[mazepos_X][mazepos_Y]=rand()%3;
     }
     maze[1][1]=PATH;
     maze[n-2][m-2]=PATH;
     for(mazepos_X=0;mazepos_X<n;mazepos_X++)
     {
         for(mazepos_Y=0;mazepos_Y<m;mazepos_Y++)
         {
              if(maze[mazepos_X][mazepos_Y]) printf("  ");
              else printf("■");
         }
         printf("\n");
     }     
     return;
}
void Initialize(STACK *varstack)
{
     varstack->Err=0;
     varstack->top=varstack->base=0;
}
待续

20 楼

接上
BOOLEAN mazePath(int (*maze)[MAX],int m,int n)
{
    STACK pathStack;
    int now_X=1,now_Y=1;
    int i,j;
    DIRECTION nowDir=NODIR;
    Initialize(&pathStack);
    do
    {
        if(maze[now_X][now_Y]!=OBTACLE && maze[now_X][now_Y]!=FOOTPRINT && judgeStack(pathStack,now_X,now_Y))
        {
            pathStack.stackX[pathStack.top]=now_X;
            pathStack.stackY[pathStack.top]=now_Y;
            nowDir=NODIR;
            if(now_X==n-2 && now_Y==m-2)
            {
                for(i=pathStack.base;i<pathStack.top;i++)
                {
                    maze[pathStack.stackX[i]][pathStack.stackY[i]]=RESPATH;
                }
                maze[n-2][m-2]=RESPATH;
                for(i=0;i<n;i++)
                {
                    for(j=0;j<m;j++)
                    {
                        if(maze[i][j]==OBTACLE) printf("■");
                        else if(maze[i][j]==RESPATH) printf("☆");
                        else printf("  ");
                    }
                    printf("\n");
                }
                return TRUE; 
            }
            pathStack.stackDir[pathStack.top]=nextDir(&now_X,&now_Y,nowDir);
            pathStack.top++;
            nowDir=NODIR;
        } 
        else
        {
             if(pathStack.top!=pathStack.base)
             {
                  pathStack.top--;
                  now_X=pathStack.stackX[pathStack.top];
                  now_Y=pathStack.stackY[pathStack.top];
                  nowDir=pathStack.stackDir[pathStack.top];
                  while(nowDir==NORTH && pathStack.top!=pathStack.base)
                  {
                      maze[now_X][now_Y]=FOOTPRINT;
                      pathStack.top--; 
                      now_X=pathStack.stackX[pathStack.top];
                      now_Y=pathStack.stackY[pathStack.top];
                      nowDir=pathStack.stackDir[pathStack.top];
                  }
                  if(pathStack.stackDir[pathStack.top]<NORTH)
                  {                                       
                      pathStack.stackX[pathStack.top]=now_X;
                      pathStack.stackY[pathStack.top]=now_Y;
                      pathStack.stackDir[pathStack.top]=nextDir(&now_X,&now_Y,nowDir);
                      pathStack.top++;
                      nowDir=NODIR;
                  }
             }
        }                   
    }while(pathStack.top!=pathStack.base);
    return FALSE;
}
待续

我来回复

您尚未登录,请登录后再回复。点此登录或注册