版权声明:反正也没有人会转,下一个 https://blog.csdn.net/drtlstf/article/details/82701127
Description
elfness被魔王抓走了,这次魔王把elfness关在一个n*m的地牢里。地牢的某个地方安装了一个带锁的门,钥匙藏在地牢的另外一个地方,elfness想要通过这个门,就必须先走到藏钥匙的地方取钥匙。刚开始的时候elfness被关在(sx,sy)的位置,而离开地牢的门在(ex,ey)的位置。elfness每分钟只能从一个位置走到相邻四个位置中的其中一个。魔王每t分钟都回地牢视察一次,若发现elfness不在原位置便会把他拎回去。经过若干次的尝试,elfness已经画出了整个地牢的地图。现在请你帮他计算能否再次成功逃亡。只要在魔王下次视察之前走到出口就算离开地牢,如果魔王回来的时候还未到出口都算逃亡失败。
Input
第一行有三个整数n,m,t。接下来的n行m列为地牢的地图,其中包括:
. 代表路
* 代表墙
@ 代表elfness的起始位置
^ 代表地牢的出口
A 代表带锁的门
a 代表钥匙
Output
输出为一行,包含一个整数。对于可以成功逃亡的情况,请输出至少需要多少分钟才能离开,如果不能则输出-1。
Sample Input
4 4 100
@..A
a.*.
***.
^…
Sample Output
11
HINT
【数据范围】
对于100%的数据,2<=n,m<=20,t>0
[分析]
BFS
一个点如果没有被访问过,走;
一个点被没带钥匙访问过,如果有钥匙,走。
代码:
#include <iostream>
#include <queue>
#define SIZE 24
using namespace std;
struct node
{
int x, y, costed;
};
node current, next1;
int visited[SIZE][SIZE];
int dx[4] = {0, 1, 0, -1}; // 四个方向
int dy[4] = {-1, 0, 1, 0};
bool keyed[SIZE][SIZE];
char a[SIZE][SIZE];
queue<node> q;
int main(void)
{
int n, m, t, i, j, k, entrancex, entrancey, exitx, exity, row, column, f = 0;
cin >> n >> m >> t;
for (i = 1; i <= n; ++i)
{
for (j = 1; j <= m; ++j)
{
cin >> a[i][j];
if (a[i][j] == '@')
{
entrancex = i;
entrancey = j;
f |= 1;
}
else if (a[i][j] == '^')
{
exitx = i;
exity = j;
f |= 2;
}
else if (a[i][j] == 'a')
{
f |= 4;
}
else if (a[i][j] == 'A')
{
row = i;
column = j;
f |= 8;
}
}
}
if ((f & 3) != 3) // 没起点没终点,不成
{
cout << -1 << endl;
return 0;
}
if ((f & 12) == 8) // 没钥匙,大门改障碍物
{
a[row][column] = '*';
}
for (i = 0; i < SIZE; ++i)
{
for (j = 0; j < SIZE; ++j)
{
visited[i][j] = -1;
if (f & 8 == 0)
{
keyed[i][j] = true;
}
else
{
keyed[i][j] = false;
}
}
}
for (i = 0; i <= n + 1; ++i)
{
a[i][0] = a[i][m+1] = '*';
}
for (j = 0; j <= m + 1; ++j)
{
a[0][j] = a[n+1][j] = '*';
}
a[entrancex][entrancey] = '.';
current.x = entrancex;
current.y = entrancey;
current.costed = 0;
visited[current.x][current.y] = 0;
keyed[current.x][current.y] = false;
q.push(current);
while (!(q.empty())) // 基本BFS
{
current = q.front();
q.pop();
if ((current.x == exitx) && (current.y == exity)) // 到达终点
{
if (current.costed < t) // 没到时间,输出结果
{
cout << current.costed << endl;
return 0;
}
else // 等于或超过限定时间,不成
{
cout << -1 << endl;
return 0;
}
}
for (k = 0; k < 4; ++k)
{
next1.x = row = current.x + dx[k];
next1.y = column = current.y + dy[k];
if ((visited[row][column] == -1) || ((visited[row][column] == 0) && (keyed[current.x][current.y]) && (!keyed[row][column])))
{
if (a[row][column] == 'a')
{
keyed[row][column] = true;
}
if (((a[row][column] != '*') && (a[row][column] != 'A')) || ((a[row][column] == 'A') && (keyed[current.x][current.y])))
{
visited[row][column] = 0;
next1.x = row;
next1.y = column;
next1.costed = current.costed + 1;
if (keyed[current.x][current.y])
{
keyed[row][column] = true;
}
q.push(next1);
}
}
}
}
cout << -1 << endl; // 到达不了,不成
return 0;
}