Hero In Maze(迷宫英雄)

文章描述了一道编程题,涉及迷宫地图和BFS(广度优先搜索)算法的应用。主人公Jesse试图在有限时间内救出被困公主,题目要求判断Jesse能否在给定时间内找到公主。给出的C++代码示例展示了如何通过BFS策略进行路径搜索并确定是否能在规定时间内救出公主。
摘要由CSDN通过智能技术生成

题目描述

500 年前,Jesse 是我国最卓越的剑客。他英俊潇洒,而且机智过人 ^_^。
突然有一天,Jesse 心爱的公主被魔王困在了一个巨大的迷宫中。Jesse 听说这个消息已经是两天以后了,他知道公主在迷宫中还能坚持 TTT 天,他急忙赶到迷宫,开始到处寻找公主的下落。 时间一点一点的过去,Jesse 还是无法找到公主。最后当他找到公主的时候,美丽的公主已经死了。从此 Jesse 郁郁寡欢,茶饭不思,一年后追随公主而去了。T_T 
500 年后的今天,Jesse 托梦给你,希望你帮他判断一下当年他是否有机会在给定的时间内找到公主。
他会为你提供迷宫的地图以及所剩的时间 TTT。请你判断他是否能救出心爱的公主。 

输入

题目包括多组测试数据。 
每组测试数据以三个整数 N,M,TN, M, TN,M,T(0<n,m≤20;t>00 \lt n, m \le 20; t \gt 00<n,m≤20;t>0)开头,分别代表迷宫的长和高,以及公主能坚持的天数。 
紧接着有 MMM 行,NNN 列字符,由 .*PS 组成。其中 . 代表能够行走的空地。* 代表墙壁,Jesse 不能从此通过。P 是公主所在的位置。 S 是 Jesse 的起始位置。 
每个时间段里 Jesse 只能选择“上、下、左、右”任意一方向走一步。输入以 0 0 0 结束。 

输出

如果能在规定时间内救出公主输出 YES,否则输出 NO。 

输入输出样例

样例输入 #1

4 4 10
....
....
....
S**P
0 0 0

样例输出 #1

YES

c++代码(bfs无函数调用):

#include<iostream>
#include<cstring>
#include<cmath>
#include<queue>  //队列
#define F(a,begin,end) for(register int a=begin;a<end;a++) //宏
using namespace std;
const int MAXN = 25;
int m, n, T;  //监狱长、宽、时间
char arr[MAXN][MAXN]; //监狱
int visited[MAXN][MAXN] = { 0 };
int step[4][2] = { 1,0,-1,0,0,1,0,-1 };//骑士行走的方向
struct steps {
    int x, y, t;
    steps(int xx, int yy, int tt) :x(xx), y(yy), t(tt) {}
};
queue<steps >q;
int main() {
    while (cin >> n >> m >> T) {  //按题目要求,先输入的是列再是行!!!
        bool flag = 0; //判断是否可以找到公主
        memset(visited, 0, sizeof(visited));//初始化
        memset(arr, 0, sizeof(arr));//初始化
        while (!q.empty()) q.pop();//将队列清空
        int x, y;
        if (m + n + T == 0) break; //样例输入终止条件
        F(i, 0, m) F(j, 0, n) {
            cin >> arr[i][j];
            if (arr[i][j] == 'S') {  //记录初始位置
                x = i;
                y = j;
            }
            if (arr[i][j] == '*') visited[i][j] = 1; //墙->不能走
        }
        q.push(steps(x, y, 0));
        visited[x][y] = 1;
        while (!q.empty()) {
            steps s = q.front();
            q.pop();
            if (arr[s.x][s.y] == 'P') {
                flag = 1;  //可以找到皇后
                if (s.t <= T) cout << "YES" << endl;
                else cout << "NO" << endl;
                break;
            }
            else {
                F(i, 0, 4) {
                    int a = s.x + step[i][0];
                    int b = s.y + step[i][1];
                    if (s.t > T) continue; //剪枝
                    if (a >= m || b >= n || a < 0 || b < 0) continue;
                    if (arr[a][b]=='*'||visited[a][b]) continue;
                    visited[a][b] = 1;
                    q.push(steps(a, b, s.t + 1));
                }
            }
        }
        if(!flag) cout<<"NO"<<endl;  //无法找到
    }
    return 0;
}

 c++代码(bfs函数调用)

#include<iostream>
#include<cstring>
#include<cmath>
#include<queue>
#define F(a,begin,end) for(register int a=begin;a<end;a++)
using namespace std;
const int MAXN = 25;
int m, n, T;
char arr[MAXN][MAXN];
int visited[MAXN][MAXN],step[4][2] = { 1,0,-1,0,0,1,0,-1 };
struct steps {
    int x, y, t;
    steps(int xx, int yy, int tt) :x(xx), y(yy), t(tt) {}
};
int bfs(int x, int y) {
    queue<steps >q;
    q.push(steps(x, y, 0));
    visited[x][y] = 1;
        while (!q.empty()) {
            steps s = q.front();
            q.pop();
            if (arr[s.x][s.y] == 'P') return s.t;
                F(i, 0, 4) {
                    int a = s.x + step[i][0];
                    int b = s.y + step[i][1];
                    if (a < m && b < n  &&a >= 0 && b >= 0 && !visited[a][b]) {
                        visited[a][b] = 1;
                        q.push(steps(a, b, s.t + 1));
                    }  
                }
        }
        return 100000000;
}
int main() {
    while (cin >> n >> m >> T) {
        int x, y;
        if (m+n+T==0)  break;
        memset(visited, 0, sizeof(visited));
        memset(arr, 0, sizeof(arr));
        F(i, 0, m) F(j, 0, n) {
                cin >> arr[i][j];
                if (arr[i][j] == 'S') x=i,y=j;
                else if (arr[i][j] == '*') visited[i][j] = 1;
            }
        if (bfs(x,y) > T) cout << "NO" << endl;
        else cout << "YES" << endl;
    }
    return 0;
}
评论 2
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值