/*ccf 201604_4
普通的bfs,但是注意当无路可走的时候是可以回到上一次走过的格子的,所以不能用普通的
标记像vis[i][j]来表示某个格子曾走过。应该采用拆点的思想,vis[i][j][t]表示t时刻走过
格子i,j。其余按照套路走即可。
*/
#include <iostream>
#include <queue>
#include <cstdio>
#include <cstring>
using namespace std;
const int maxn = 105;
const int dx[] = {0, 0, 1, -1};
const int dy[] = {1, -1, 0, 0};
int board[maxn][maxn], s[maxn][maxn], e[maxn][maxn];
int n, m, t;
bool vis[maxn][maxn][maxn];
struct Node
{
int row, col, time;
Node(int r, int c, int t):row(r), col(c), time(t) {}
Node(){}
};
inline bool inside(int x, int y)
{
return x >= 0 && x < n && y >= 0 && y < m;
}
inline bool safe(int x, int y, int t)
{
return t < s[x][y] || t > e[x][y];
}
int bfs()
{
queue<Node> q;
q.push(Node(0, 0, 0));
while(!q.empty()) {
Node x = q.front(); q.pop();
//printf("#%d %d = %d\n", x.row, x.col, x.time);
if(x.row == n-1 && x.col == m-1) return x.time;
if(vis[x.row][x.col][x.time]) continue;
vis[x.row][x.col][x.time] = true;
for(int d = 0; d < 4; d++) {
int nx = x.row + dx[d];
int ny = x.col + dy[d];
if(inside(nx, ny) && safe(nx, ny, x.time + 1) && !vis[nx][ny][x.time+1]) {
q.push(Node(nx, ny, x.time + 1));
}
}
}
}
int main()
{
//freopen("in.txt", "r", stdin);
memset(board, 0, sizeof(board));
memset(s, 0, sizeof(s)); memset(e, 0, sizeof(e));
memset(vis, 0, sizeof(vis));
scanf("%d%d%d", &n, &m, &t);
int r, c, a, b;
for(int i = 0; i < t; i++) {
scanf("%d%d%d%d", &r, &c, &a, &b);
r--; c--;
s[r][c] = a; e[r][c] = b;
}
printf("%d\n", bfs());
return 0;
}
201604-4(游戏)
最新推荐文章于 2020-02-29 20:21:40 发布