问题描述:
给你一个整数M表示流行的个数,然后给你M组数据每组包含3个整数,分别表示坐标和降落的时间。
题目链接:点击打开链接
思路:
先把时间都标记好,在跑一遍BFS即可。
注意:走过的点不能再走!!!还要注意时间,这种解法很费时所以将输入输出流换成了scanf,,,,,
代码:
#include<iostream>
#include<cstdio>
#include<queue>
#include<cstring>
#define INF 0x3f3f3f3f
using namespace std;
struct P
{
int x, y, z;
};
const int MAX = 302;
int field[MAX][MAX], foot[MAX][MAX];//foot用来判断是否该点是否走过
int dx[4] = {1, 0, -1, 0}, dy[4] = {0, 1, 0, -1};
int BFS();
int main()
{
int t, arr[MAX][MAX];
while(~scanf("%d", &t))
{
//把所有点都给赋值为INF
for(int i = 0; i < 302; i++)
for(int j = 0; j < 302; j++) field[i][j] = INF;
//给数组foot全部赋值为0,表示所有的点都没走过
memset(foot, 0, sizeof(foot));
//给所有的点标记上时间(有流星来的时间)
while(t--)
{
int x, y, z;
scanf("%d%d%d", &x, &y, &z);
if(field[x][y] > z)
field[x][y] = z;
for(int i = 0; i < 4; i++)
{
int nx = x + dx[i], ny = y + dy[i];
if(nx >= 0 && nx <= 302 && ny >= 0 &&
ny <= 302 && field[nx][ny] > z)
field[nx][ny] = z;
}
}
//跑一遍BFS即可
int res = BFS();
cout << res << endl;
}
}
int BFS()
{
queue<P> que;
que.push((P)
{
0, 0, 0
});
while(que.size())//直到队列长度为0
{
P p = que.front();
que.pop();
if(field[p.x][p.y] == INF) return p.z;
if(foot[p.x][p.y]) continue;//走过不能再走了(排除走过的点重新走的可能)
foot[p.x][p.y] = 1;//标记该点已经走过
for(int i = 0; i < 4; i++)
{
P n;
n.x = p.x + dx[i];
n.y = p.y + dy[i];
n.z = p.z + 1;
if(0 <= n.x && n.x < 302 && 0 <= n.y && n.y < 302 &&
n.z < field[n.x][n.y] && foot[n.x][n.y] == 0)
{
que.push(n);
}
}
}
return -1;
}