HDU 1484 dfs 路径记录

本文介绍了一种解决迷宫寻路问题的算法实现。通过深度优先搜索(DFS)策略,文章详细阐述了如何在存在障碍的情况下寻找从起点到终点的最短路径,并记录这一路径。文中使用了二维数组来表示迷宫地图,并通过特定的数据结构记录每个节点的前驱节点以回溯整个路径。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

本题难点有两个,一个是如何记录路径,还有就是如何设置障碍物,即障碍物的方向与扩展步数的方向要保持一致

#include <cstdio>
#include <cstring>
#include <algorithm>
#include <queue>
#include <stack>
#include <climits>
using namespace std;

int dx[] = {0,-1,0,1};
int dy[] = {1,0,-1,0};  //右上左下

int graph[9][9][4];
int dist[9][9] , pre[9][9][2] ; //pre是前驱坐标
int sx,sy,ex,ey;
int wx1,wy1,wx2,wy2;

void dfs(int x,int y,int cnt){
    for(int i=0;i<4;i++){  //查看当前位置的四个方向是否可以走
        if(graph[x][y][i]) continue;  //若该方向不能走
        //若该方向可以走,则沿着该方向进行扩展
        int xx = x+dx[i];  //扩展新的位置
        int yy = y+dy[i];
        if(xx<1 || yy<1 || xx>6 || yy>6)  continue;
        if(cnt+1 > dist[xx][yy]) continue; //若当前的代价更大,则一定不能产生最优解
        dist[xx][yy] = cnt+1;
        pre[xx][yy][0] = x;
        pre[xx][yy][1] = y;
        dfs(xx,yy,cnt+1);
    }
}

void path(){
    int x = ex,y = ey;  //倒序查找
    int px = pre[x][y][0] , py = pre[x][y][1];
    stack<char> st;
    while(1){
        if(x==px){  //同一行
            if(py<y)
                st.push('E');
            else
                st.push('W');
        }
        else{       //同一列
            if(px<x)
                st.push('S');
            else
                st.push('N');
        }
        if(px==sx && py==sy) break; //递归到了起点
        x = px;
        y = py;
        px = pre[x][y][0];
        py = pre[x][y][1];
    }
    while(!st.empty()){
        printf("%c",st.top());
        st.pop();
    }
    printf("\n");
}


int main(){
    while(scanf("%d%d",&sy,&sx)){
        if(sx==0 && sy==0) break;
        scanf("%d%d",&ey,&ex);
        //初始化
        for(int i=0;i<9;i++)
            for(int j=0;j<9;j++){
                dist[i][j] = INT_MAX;
                memset(graph,0,sizeof(graph));
            }
        //读取三个墙的位置,起点及终点
        for(int i=0;i<3;i++){   //构造三面墙的矩阵
            scanf("%d%d%d%d",&wy1,&wx1,&wy2,&wx2);
            if(wx1==wx2){   //同一行
                for(int j=wy1+1;j<=wy2;j++){
                    graph[wx1][j][3] = 1;  //下部
                    graph[wx1+1][j][1] = 1;  //上部
                }
            }
            else{   //同一列
                for(int j=wx1+1;j<=wx2;j++){
                    graph[j][wy1][0] = 1;
                    graph[j][wy1+1][2] = 1;
                }
            }
        }
        dfs(sx,sy,0);  //起点,当前步数为0
        path();
    }
    return 0;
}

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值