打完多校赛网络赛后 对这题有点感想,Barareh on Fire 点击打开链接
题意:你在一个荒野,初始位置为 s 你要走到出口 t 但是 荒野上有火 f ,火每隔 k 秒向周围蔓延(八个方向),你可以向4个方向走动,每走一步花费1秒。求 走到出口的最小时间 如果走不到出口 输出“Impossible”
思路 :先打出火的蔓延时间表,然后再bfs一下就好了。
一开始,我们队用dfs打表,TLE了,后来 改用bfs打表,每碰到火就进行一次bfs,所幸时间给得多,这题擦边过了。
后来,看到大佬的操作才发现,我们写的代码是多么的丑!大佬直接将所有的初始火加入队列,然后bfs一遍就打好表了。
比我们写的不知道要高效多少!希望自己在以后写题时 能够多多思考。
#include<iostream>
#include<cstdio>
#include<cstring>
#include<algorithm>
#include<map>
#include<queue>
#include<set>
#include<string>
#include<cmath>
#define test printf("***\n")
#define mlr(a) memset((a),0,sizeof((a)))
#define mmx(a) memset((a),0x3f,sizeof((a)))
#define ka getchar();getchar()
#define ka1 getchar()
#define iis std::ios::sync_with_stdio(false)
using namespace std;
typedef long long LL;
typedef unsigned long long uLL;
const int N = 105;
const int INF = 1e9;
const double eps = 1e-8;
int dx[10]={1,1,1,0,0,-1,-1,-1};
int dy[10]={-1,0,1,-1,1,-1,0,1};
int dix[5]={0,0,1,-1},diy[5]={-1,1,0,0};
int fir[N][N];
int a1,a2,b1,b2;
char ar[N][N];
int n,m,k;
int vis[N][N];
struct two{
int x,y,t;
};
void init()
{
two temp,temp2;
queue<two> que;
while(!que.empty())que.pop();
for(int i=0;i<n;i++)
{
for(int j=0;j<m;j++)
{
if(ar[i][j]=='s'){
a1=i;
a2=j;
}
else if(ar[i][j]=='t')
{
b1=i;b2=j;
}
if(ar[i][j]=='f')
{
temp.x=i;
temp.y=j;
fir[i][j]=0;
temp.t=0;
que.push(temp);
}
else fir[i][j]=INF;
}
}
while(que.size())
{
temp=que.front();
que.pop();
for(int i=0;i<8;i++)
{
temp2.x=temp.x+dx[i];
temp2.y=temp.y+dy[i];
temp2.t=temp.t+k;
if(temp2.x>=0&&temp2.x<n&&temp2.y>=0&&temp2.y<m)
{
if( fir[temp2.x][temp2.y]>temp2.t)
{
fir[temp2.x][temp2.y]=temp2.t;
que.push(temp2);
}
}
}
}
}
int bfs(){
two temp,temp2;
queue<two>que;
while(!que.empty())que.pop();
temp.x=a1;
temp.y=a2;
temp.t=0;
que.push(temp);
memset(vis,0,sizeof(vis));
vis[a1][a2]=1;
while(que.size())
{
temp=que.front();
que.pop();
if(temp.x==b1&&temp.y==b2)return temp.t;
for(int i=0;i<4;i++)
{
temp2.x=temp.x+dix[i];
temp2.y=temp.y+diy[i];
temp2.t=temp.t+1;
if(temp2.x>=0&&temp2.x<n&&temp2.y>=0&&temp2.y<m&&vis[temp2.x][temp2.y]==0)
{
if( fir[temp2.x][temp2.y]>temp2.t)
{
vis[temp2.x][temp2.y]=1;
que.push(temp2);
}
}
}
}
return -1;
}
int main(){
while(~scanf("%d%d%d",&n,&m,&k)&&(n+m+k)){
for(int i=0;i<n;++i){
scanf("%s",ar[i]);
}
init();
int tem=bfs();
if(tem==-1)printf("Impossible\n");
else printf("%d\n",tem);
}
return 0;
}