| 网站首页 | 业界新闻 | 小组 | 威客 | 人才 | 下载频道 | 博客 | 代码贴 | 在线编程 | 编程论坛
欢迎加入我们,一同切磋技术
用户名:   
 
密 码:  
共有 1860 人关注过本帖, 1 人收藏
标题:关于用栈解迷宫的算法
只看楼主 加入收藏
lwlls668
Rank: 2
等 级:论坛游民
帖 子:59
专家分:72
注 册:2010-4-9
结帖率:100%
收藏(1)
已结贴  问题点数:50 回复次数:23 
关于用栈解迷宫的算法
#include "stdafx.h"
#include<stdio.h>
#include<stdlib.h>
int nums[100][100];//储存迷宫的数据,0代表可以通过,1代表有障碍物
int line,row;// line代表多少列,row 代表多少行
struct node
{
    int x;//代表当前节点的x坐标
    int y;//y坐标
    struct node*next;//指向下个节点
    struct node*tail;//指向前一个节点
};
void insert(node*top,int i,int j)//插入新位置,向前走一步
{
    node*n;
    n=(node*)malloc(sizeof(node));
    n->x=j;
    n->y=i;
    n->next=NULL;
    n->tail=top;
    top->next=n;
    top=n;
}
void delet(node*top)//出栈,把当前的节点删除掉,向后退一步
{
    node*p=top;
    top=p->tail;
    free(p);
}
int move(node*top)//判断每个位置的走向可能,按顺时针搜寻,返回不同的int
{
    int i=0;
    if(top->x+1!=top->tail->x&&nums[top->x+1][top->y]==0)//如果top的x+1不等于上一步的x,就是说没有往回走循环。还要判断这个方向的nums[][]==0 才能走这条路,这是第一种情况,返回1;
            return (i=1);
    if(top->y+1!=top->tail->y&&nums[top->x][top->y+1]==0)//如果top的y+1不等于上一步的y,就是说没有往回走循环。还要判断这个方向的nums[][]==0 才能走这条路,这是第二种情况,返回2;
            return  (i=2);
    if(top->x-1!=top->tail->x&&nums[top->x-1][top->y]==0)
            return (i=3);
    if(top->y-1!=top->tail->y&&nums[top->x][top->y-1]==0)
            return  (i=4);
    return i;//当上面的假设都不成立就代表四周都不能走了,返回0;
}
int main()
{
    int i,j;
    node*head,*top;//head只是保留初始点,top才是最远的一个点
    printf("请输入一共有多少行?多少列?");
    scanf("%d%d",&row,&line);
    for(i=0;i<99;i++)//初始化,把周围的当成是1  那就不用判断是否出界了
        for(j=0;j<99;j++)
            nums[i][j]=1;
    for(i=1;i<=row;i++)
        for(j=1;j<=line;j++)
            scanf("%d",&nums[i][j]);
    head=(node*)malloc(sizeof(node));//第一步,在起点,栈的开始
    head->next=head->tail=NULL;
    head->x=head->y=1;
    top=head;
    while(top->x!=line||top->y!=row)//当没达到终点,循环
    {
        switch(move(top))
        {
        case 0:
            if(top->tail==NULL)//如果当前是原点,而且move(top)返回的是0,说明当前没有出路了。其它的返还值对应操作
            {
                printf("没路了");
                exit(0);
            }
            else
            {
                nums[top->x][top->y]=1;
                delet(top);// 如果不是第一个点,出栈
               
            }
             break;
        case 1://如果这个点符合条件,入栈,把下一个点作为前方探路点(向这个方向走了一步)
            insert(top,top->x+1,top->y);
            break;
        case 2:
            insert(top,top->x,top->y+1);
            break;
        case 3:
            insert(top,top->x-1,top->y);
            break;
        case 4:
            insert(top,top->x,top->y-1);
            break;
        }
    }            
    return 0;
}
这是自己写的,原理很简单,就是利用栈的特性一步步搜索下去。
我想了很久也没想出哪儿错了,我希望能先找出这个的问题再看更好的方法,希望谁能帮我看看,应该是指针出错了,我指针不懂。
谢谢了。
搜索更多相关主题的帖子: 算法 解迷宫 
2010-11-05 23:55
outsider_scu
Rank: 9Rank: 9Rank: 9
等 级:蜘蛛侠
威 望:3
帖 子:430
专家分:1333
注 册:2010-10-21
收藏
得分:0 
不想看。。
不过我以前也用栈写了一个,就是回溯嘛。。

编程的道路上何其孤独!
2010-11-06 00:29
lwlls668
Rank: 2
等 级:论坛游民
帖 子:59
专家分:72
注 册:2010-4-9
收藏
得分:0 
  回溯,我不知道哪错了。感觉这样是最普通方法,但这个我都不知道怎么错了。郁闷呀
2010-11-06 00:58
遮天云
Rank: 11Rank: 11Rank: 11Rank: 11
来 自:农村一小伙
等 级:贵宾
威 望:12
帖 子:1132
专家分:2671
注 册:2010-6-1
收藏
得分:20 
程序代码:
#define N 5
#define M 5
#include<stdio.h>
#include<malloc.h>
#include<conio.h>
typedef struct node
{
    int row;
    int col;
    struct node *next;
}Mlink;

 Mlink *Stack;
int MazePath()//寻找迷宫路径,若有则返回1,否则返回零
{
    int maze[N+2][M+2],i,j,x1,y1,x2,y2,r,c;
    //开始设置一圈障碍
    for(i=0;i<N+2;i++)//第零行设置障碍
        maze[0][i]=1;
    for(j=1;j<M+2;j++)//第零列设置障碍
        maze[j][0]=1;
    for(i=1;i<N+2;i++)//最后一行设置障碍
        maze[N+1][i]=1;
    for(j=1;j<M+1;j++)//最后一列设置障碍
        maze[j][M+1]=1;
    Mlink *p;
    printf("创建%d*%d迷宫矩阵\n",N,M);
    for(i=1;i<=N;i++)
    {
        for(j=1;j<=M;j++)
        {
            scanf("%d",&maze[i][j]);
        //    fflush(stdin);
        }
    //    printf("\n");
    }
    printf("验证输出迷宫矩阵\n");
        for(i=0;i<N+2;i++)
        {
            for(j=0;j<M+2;j++)
                printf("%2d",maze[i][j]);
            printf("\n");
        }
                
    printf("输入迷宫的入口;\n");
    scanf("%d%d",&x1,&y1);
    fflush(stdin);

    Stack=NULL;
    p=(Mlink *)malloc(sizeof(Mlink));//将迷宫的入口位址入栈
    p->row=x1;
    p->col=y1;
    p->next=Stack;
    Stack=p;
    printf("验证%d\n",maze[1][1]);
        printf("输入迷宫的出口:\n");
    scanf("%d%d",&x2,&y2);
    fflush(stdin);
    maze[Stack->row][Stack->col]=1;//把入口位置设置为障碍,以阻止稍后的搜索在经过这个位置
    r=p->row;
    c=p->col;
    printf("x2=%d y2=%d\n",x2,y2);
    while(((r!=x2)||(c!=y2))&&Stack!=NULL)
    //考察当前位置的东南西北方向邻居是否有障碍
    //若没有,则沿着这个方向继续搜索,若都是障碍,则将栈顶元素出栈
    {
        if(maze[Stack->row][Stack->col+1]==0)
        {
            //printf("我");
            //printf("r=%d c=%d ",Stack->row,Stack->col+1);
            p=(Mlink *)malloc(sizeof(Mlink));
            p->row=Stack->row;
            p->col=Stack->col+1;
            r=p->row;
            c=p->col;
            p->next=Stack;
            Stack=p;
            maze[r][c]=1;//搜索过的位置设置为障碍,以阻止在后续搜索中在经过这个位置
        //    printf("maze[%d][%d]=%2d\n",r,c,maze[r][c]);
        //    getch();
            //fflush(stdin);
        }
        else if(maze[Stack->row][Stack->col-1]==0)
        {
        //    printf("爱");
        //    printf("r=%d c=%d ",Stack->row,Stack->col-1);    
            p=(Mlink *)malloc(sizeof(Mlink));
            p->row=Stack->row;
            p->col=Stack->col-1;
            r=p->row;
            c=p->col;
            p->next=Stack;
            Stack=p;
            maze[r][c]=1;//搜索过的位置设置为障碍,以阻止在后续搜索中在经过这个位置
        //    printf("maze[%d][%d]=%2d\n",r,c,maze[r][c]);
        //    getch();
        //    fflush(stdin);

        }
        else if(maze[Stack->row+1][Stack->col]==0)
        {
            //printf("编");
        //    printf("r=%d c=%d ",Stack->row+1,Stack->col);
            p=(Mlink *)malloc(sizeof(Mlink));
            p->row=Stack->row+1;
            p->col=Stack->col;
            r=p->row;
            c=p->col;
            p->next=Stack;
            Stack=p;
            maze[r][c]=1;//搜索过的位置设置为障碍,以阻止在后续搜索中在经过这个位置
        //    printf("maze[%d][%d]=%2d\n",r,c,maze[r][c]);
        //    getch();
        //    fflush(stdin);
        }
        else if(maze[Stack->row-1][Stack->col]==0)
        {
            
            //printf("程");
        //    printf("r=%d c=%d ",Stack->row-1,Stack->col);
            p=(Mlink *)malloc(sizeof(Mlink));
            p->row=Stack->row-1;
            p->col=Stack->col;
            r=p->row;
            c=p->col;
            p->next=Stack;
            Stack=p;
            maze[r][c]=1;//搜索过的位置设置为障碍,以阻止在后续搜索中在经过这个位置
        //    printf("maze[%d][%d]=%2d\n",r,c,maze[r][c]);
        //    getch();
        //    fflush(stdin);
        }
        else //如果入到障碍说明路不通,栈顶元素出栈
        {
            //printf("牛\n");
        //    getch();
        //    fflush(stdin);
            p=Stack;
            Stack=Stack->next;
            free(p);
        }
    }
    if(Stack==NULL)//如果栈空,说明不存在通路
        return 0;
    else //否则存在通路
        return 1;
}            
int main()
{
    int i;
    Mlink *p;
    i=MazePath();
    if(i==1)
    {
        p=Stack;
        printf("其中的一条路线为:\n");
        while(p!=NULL)
        {
            printf("%3d%3d\n",p->row,p->col);
            p=p->next;
        }
    }
    else 
        printf("NO PATH!\n");
    return 0;
}
楼主这是我写的,奋战了今天一上午了,注释掉的部分是我分布调试的思索过程,我觉得这样容易发现错误(事实证明这样做对我的分析题目很用帮助)你可以不看它
2010-11-06 10:30
遮天云
Rank: 11Rank: 11Rank: 11Rank: 11
来 自:农村一小伙
等 级:贵宾
威 望:12
帖 子:1132
专家分:2671
注 册:2010-6-1
收藏
得分:0 
程序代码:
//#include "stdafx.h"
#include<stdio.h>
#include<stdlib.h>
#include<malloc.h>
int nums[100][100];//储存迷宫的数据,0代表可以通过,1代表有障碍物
int line,row;// line代表多少列,row 代表多少行
struct node
{
    int x;//代表当前节点的x坐标
    int y;//y坐标
    struct node*next;//指向下个节点
    struct node*tail;//指向前一个节点
};
void insert(struct node *top,int i,int j)//插入新位置,向前走一步
{
    struct node*n;
    n=(struct node*)malloc(sizeof(struct node));
    n->x=j;
    n->y=i;
    n->next=NULL;
    n->tail=top;
    top->next=n;
    top=n;
}
void delet(struct node*top)//出栈,把当前的节点删除掉,向后退一步
{
    struct node *p=top;
    top=p->tail;
    free(p);
}
int move(struct node *top)//判断每个位置的走向可能,按顺时针搜寻,返回不同的int
{
    int i=0;
    if(top->x+1!=top->tail->x&&nums[top->x+1][top->y]==0)//如果top的x+1不等于上一步的x,就是说没有往回走循环。还要判断这个方向的nums[][]==0 才能走这条路,这是第一种情况,返回1;
            return (i=1);
    if(top->y+1!=top->tail->y&&nums[top->x][top->y+1]==0)//如果top的y+1不等于上一步的y,就是说没有往回走循环。还要判断这个方向的nums[][]==0 才能走这条路,这是第二种情况,返回2;
            return  (i=2);
    if(top->x-1!=top->tail->x&&nums[top->x-1][top->y]==0)
            return (i=3);
    if(top->y-1!=top->tail->y&&nums[top->x][top->y-1]==0)
            return  (i=4);
    return i;//当上面的假设都不成立就代表四周都不能走了,返回0;
}
int main()
{
    int i,j;
   struct node *head,*top;//head只是保留初始点,top才是最远的一个点
    printf("请输入一共有多少行?多少列?");
    scanf("%d%d",&row,&line);
    for(i=0;i<99;i++)//初始化,把周围的当成是1  那就不用判断是否出界了
        for(j=0;j<99;j++)
            nums[i][j]=1;
    for(i=1;i<=row;i++)
        for(j=1;j<=line;j++)
            scanf("%d",&nums[i][j]);
    head=(struct node*)malloc(sizeof(struct node));//第一步,在起点,栈的开始
    head->next=head->tail=NULL;
    head->x=head->y=1;
    top=head;
    while(top->x!=line||top->y!=row)//当没达到终点,循环
    {
        switch(move(top))
        {
        case 0:
            if(top->tail==NULL)//如果当前是原点,而且move(top)返回的是0,说明当前没有出路了。其它的返还值对应操作
            {
                printf("没路了");
                exit(0);
            }
            else
            {
                nums[top->x][top->y]=1;
                delet(top);// 如果不是第一个点,出栈
               
            }
             break;
        case 1://如果这个点符合条件,入栈,把下一个点作为前方探路点(向这个方向走了一步)
            insert(top,top->x+1,top->y);
            break;
        case 2:
            insert(top,top->x,top->y+1);
            break;
        case 3:
            insert(top,top->x-1,top->y);
            break;
        case 4:
            insert(top,top->x,top->y-1);
            break;
        }
    }            
    return 0;
}
这是我给你改后的,没错误了,但是我没运行,这就交给你了,你犯了个不该犯的错。结点申明按照你写的,应该写出struct node *head ,*top等,而不是node *head
2010-11-06 10:39
wujieru
Rank: 10Rank: 10Rank: 10
等 级:青峰侠
威 望:1
帖 子:1108
专家分:1939
注 册:2010-10-9
收藏
得分:0 
楼上就是爱出风头
2010-11-06 11:29
遮天云
Rank: 11Rank: 11Rank: 11Rank: 11
来 自:农村一小伙
等 级:贵宾
威 望:12
帖 子:1132
专家分:2671
注 册:2010-6-1
收藏
得分:0 
以下是引用wujieru在2010-11-6 11:29:58的发言:

楼上就是爱出风头

我都怀疑你来这论坛干嘛~。对我有意见你提出来,什么叫爱出风头,我还没那资本,有那本事我也不像某些人装B,我来这论坛是为了学习的,事实证明我在这学到了不少,但既然受恩与论坛,就要图回报,我帮忙解决自己力所能及的问题怎么着你了???????我没招你惹你吧?,有这个闲工夫你去帮助别人解决问题啊,跟我在这瞎搅和什么???,我出不出风头不是由你个人来定的,我只知道我现在能做的就是帮助别人解决我力所能及的问题!!!!!,
2010-11-06 11:49
lwlls668
Rank: 2
等 级:论坛游民
帖 子:59
专家分:72
注 册:2010-4-9
收藏
得分:0 
o(︶︿︶)o     先不说话,自己继续找,这儿继续等。希望谁能告诉我哪儿是致命的错误。谢谢了。
2010-11-06 11:56
BlueGuy
Rank: 16Rank: 16Rank: 16Rank: 16
等 级:版主
威 望:29
帖 子:4476
专家分:4055
注 册:2009-4-18
收藏
得分:0 
以下是引用遮天云在2010-11-6 11:49:36的发言:

 
我都怀疑你来这论坛干嘛~。对我有意见你提出来,什么叫爱出风头,我还没那资本,有那本事我也不像某些人装B,我来这论坛是为了学习的,事实证明我在这学到了不少,但既然受恩与论坛,就要图回报,我帮忙解决自己力所能及的问题怎么着你了???????我没招你惹你吧?,有这个闲工夫你去帮助别人解决问题啊,跟我在这瞎搅和什么???,我出不出风头不是由你个人来定的,我只知道我现在能做的就是帮助别人解决我力所能及的问题!!!!!,
来增加论坛点击率的

我就是真命天子,顺我者生,逆我者死!
2010-11-06 12:20
lwlls668
Rank: 2
等 级:论坛游民
帖 子:59
专家分:72
注 册:2010-4-9
收藏
得分:0 
创建5*5迷宫矩阵
验证输出迷宫矩阵
 1 1 1 1 1 1 1
 1 0 0 1 1 0 1
 1 1 0 1 0 0 1
 1 0 0 1 0 1 1
 1 1 0 1 0 0 1
 1 1 0 0 0 0 1
 1 1 1 1 1 1 1
输入迷宫的入口;
1 1
验证0
输入迷宫的出口:
5 1
x2=5 y2=1
请按任意键继续. . .



我还不知道4楼的是不是有点问题,你一来就把“后路”堵死了,那如果一最初是判断错误了方向,正确结果是要通过这个点的另一个方向,而你却把这个点都堵死了,那也就是说你不可能再走这个点的正确的方向,结果不就是NO PATH!了吗。还有,我很难理解你建立坐标是x,y颠倒的···其它的可以。

回到我的问题,我还没找出我哪错了···
2010-11-06 12:28
快速回复:关于用栈解迷宫的算法
数据加载中...
 
   



关于我们 | 广告合作 | 编程中国 | 清除Cookies | TOP | 手机版

编程中国 版权所有,并保留所有权利。
Powered by Discuz, Processed in 0.019542 second(s), 7 queries.
Copyright©2004-2024, BCCN.NET, All Rights Reserved