FZU 2196 Escape(多源bfs)
Problem 2196 Escape
Accept: 123 Submit: 678
Time Limit: 1000 mSec Memory Limit : 32768 KB
Problem Description
小明进入地下迷宫寻找宝藏,找到宝藏后却发生地震,迷宫各处产生岩浆,小明急忙向出口处逃跑。如果丢下宝藏,小明就能迅速离开迷宫,但小明并不想轻易放弃自己的辛苦所得。所以他急忙联系当程序员的朋友你(当然是用手机联系),并告诉你他所面临的情况,希望你能告诉他是否能成功带着宝藏逃脱。
Input
有多组测试数据。
每组测试数据第一行是一个整数T,代表接下去的例子数。(0<=T<=10)
接下来是T组例子。
每组例子第一行是两个整数N和M。代表迷宫的大小有N行M列(0<=N,M<=1000)。
接下来是一个N*M的迷宫描述。
S代表小明的所在地。
E代表出口,出口只有一个。
.代表可以行走的地方。
!代表岩浆的产生地。(这样的地方会有多个,其个数小于等于10000)
#代表迷宫中的墙,其不仅能阻挡小明前进也能阻挡岩浆的蔓延。
小明携带者宝藏每秒只能向周围移动一格,小明不能碰触到岩浆(小明不能和岩浆处在同一格)。
岩浆每秒会向四周不是墙的地方蔓延一格。
小明先移动完成后,岩浆才会蔓延到对应的格子里。
小明能移动到出口,则小明顺利逃脱。
Output
每组测试数据输出只有一行“Yes”或者“No”。“Yes”代表小明可以成功逃脱。否则输出“No”。
Sample Input
3 5 5 ....! S.... #.... !#... #E... 2 2 S. !E 2 2 SE !.
Sample Output
Yes No Yes
Source
福州大学第十二届程序设计竞赛
题目链接 :http://acm.fzu.edu.cn/problem.php?pid=2196
分析:多源bfs的裸题,由于对题意理解错误,wa的我怀疑人生,还因此输了一杯奶茶,郁闷。。。
一开始发现只有SE!时应该输出yes,这就让我误以为火每次应该是比人后到一步的
于是我写出了下面这个让我wa一天的代码:
1 #include<iostream> 2 #include<cstdio> 3 #include<cstring> 4 #include<queue> 5 #include<algorithm> 6 using namespace std; 7 typedef long long ll; 8 char s[1105][1105]; 9 int vis[1105][1105]; 10 int h[1105][1105]; 11 int dx[10]={0,0,1,-1}; 12 int dy[10]={1,-1,0,0}; 13 int T,n,m,sx,sy,ex,ey,ans; 14 struct node{ 15 int x,y,time; 16 }; 17 bool check(int x,int y){ 18 if(x<1||x>n||y<1||y>m||s[x][y]=='#'||vis[x][y])return false; 19 return true; 20 } 21 void init(){ 22 for(int i=0;i<=n;i++){ 23 for(int j=0;j<=m;j++){ 24 vis[i][j]=0; 25 h[i][j]=1e9; 26 } 27 } 28 } 29 void init1(){ 30 for(int i=0;i<=n;i++){ 31 for(int j=0;j<=m;j++){ 32 vis[i][j]=0; 33 } 34 } 35 } 36 void bfs(){ 37 init(); 38 queue<node>q; 39 node now,next; 40 now.time=1; 41 for(int i=1;i<=n;i++){ 42 for(int j=1;j<=m;j++){ 43 if(s[i][j]=='!'){ 44 vis[i][j]=1; 45 now.x=i,now.y=j; 46 h[i][j]=1; 47 q.push(now); 48 } 49 else if(s[i][j]=='S'){ 50 sx=i,sy=j; 51 } 52 else if(s[i][j]=='E'){ 53 ex=i,ey=j; 54 } 55 } 56 } 57 while(!q.empty()){ 58 now=q.front(); 59 q.pop(); 60 for(int i=0;i<4;i++){ 61 next.x=now.x+dx[i]; 62 next.y=now.y+dy[i]; 63 next.time=now.time+1; 64 if(check(next.x,next.y)){ 65 vis[next.x][next.y]=1; 66 h[next.x][next.y]=next.time; 67 q.push(next); 68 } 69 } 70 } 71 } 72 void bfs1(){ 73 init1(); 74 queue<node>q; 75 node now,next; 76 now.x=sx,now.y=sy,now.time=0; 77 q.push(now); 78 vis[sx][sy]=1; 79 while(!q.empty()){ 80 now=q.front(); 81 q.pop(); 82 for(int i=0;i<4;i++){ 83 next.x=now.x+dx[i]; 84 next.y=now.y+dy[i]; 85 next.time=now.time+1; 86 if(next.x==ex&&next.y==ey&&next.time<h[ex][ey]){ 87 ans=1; 88 return; 89 } 90 if(check(next.x,next.y)){ 91 if(next.time<h[next.x][next.y]){ 92 vis[next.x][next.y]=1; 93 q.push(next); 94 } 95 } 96 } 97 } 98 } 99 int main(){ 100 scanf("%d",&T); 101 while(T--){ 102 scanf("%d%d",&n,&m); 103 for(int i=1;i<=n;i++){ 104 scanf("%s",s[i]+1); 105 } 106 ans=0; 107 bfs(); 108 bfs1(); 109 if(ans)printf("Yes\n"); 110 else printf("No\n"); 111 } 112 }
而实际上火只有在终点的时候人与火同时到达不会影响,否则人跟火同时到达一个点的话会被火烧(好气,应该早点想到的)。
1 #include<iostream> 2 #include<cstdio> 3 #include<cstring> 4 #include<queue> 5 #include<algorithm> 6 using namespace std; 7 typedef long long ll; 8 char s[1005][1005]; 9 int vis[1005][1005]; 10 int h[1005][1005]; 11 int dx[10]={0,0,1,-1}; 12 int dy[10]={1,-1,0,0}; 13 int T,n,m,sx,sy,ex,ey,ans; 14 struct node{ 15 int x,y,time; 16 }; 17 bool check(int x,int y){ 18 if(x<1||x>n||y<1||y>m||s[x][y]=='#'||vis[x][y])return false; 19 return true; 20 } 21 void init(){ 22 for(int i=0;i<=n;i++){ 23 for(int j=0;j<=m;j++){ 24 vis[i][j]=0; 25 h[i][j]=1e9; 26 } 27 } 28 } 29 void init1(){ 30 for(int i=0;i<=n;i++){ 31 for(int j=0;j<=m;j++){ 32 vis[i][j]=0; 33 } 34 } 35 } 36 void bfs(){ 37 init(); 38 queue<node>q; 39 node now,next; 40 now.time=0; 41 for(int i=1;i<=n;i++){ 42 for(int j=1;j<=m;j++){ 43 if(s[i][j]=='!'){ 44 vis[i][j]=1; 45 now.x=i,now.y=j; 46 h[i][j]=0; 47 q.push(now); 48 } 49 else if(s[i][j]=='S'){ 50 sx=i,sy=j; 51 } 52 else if(s[i][j]=='E'){ 53 ex=i,ey=j; 54 } 55 } 56 } 57 while(!q.empty()){ 58 now=q.front(); 59 q.pop(); 60 for(int i=0;i<4;i++){ 61 next.x=now.x+dx[i]; 62 next.y=now.y+dy[i]; 63 next.time=now.time+1; 64 if(check(next.x,next.y)){ 65 vis[next.x][next.y]=1; 66 h[next.x][next.y]=next.time; 67 q.push(next); 68 } 69 } 70 } 71 } 72 void bfs1(){ 73 init1(); 74 queue<node>q; 75 node now,next; 76 now.x=sx,now.y=sy,now.time=0; 77 q.push(now); 78 vis[sx][sy]=1; 79 while(!q.empty()){ 80 now=q.front(); 81 q.pop(); 82 for(int i=0;i<4;i++){ 83 next.x=now.x+dx[i]; 84 next.y=now.y+dy[i]; 85 next.time=now.time+1; 86 if(check(next.x,next.y)){ 87 if(next.x==ex&&next.y==ey&&next.time<=h[ex][ey]){ 88 ans=1; 89 return; 90 } 91 if(next.time<h[next.x][next.y]){ 92 vis[next.x][next.y]=1; 93 q.push(next); 94 } 95 } 96 } 97 } 98 } 99 int main(){ 100 scanf("%d",&T); 101 while(T--){ 102 scanf("%d%d",&n,&m); 103 for(int i=1;i<=n;i++){ 104 scanf("%s",s[i]+1); 105 } 106 ans=0; 107 bfs(); 108 bfs1(); 109 if(ans)printf("Yes\n"); 110 else printf("No\n"); 111 } 112 }