码迷,mamicode.com
首页 > 其他好文 > 详细

uva 11624 大火蔓延的迷宫 Fire!(两次bfs)

时间:2015-05-16 09:10:49      阅读:144      评论:0      收藏:0      [点我收藏+]

标签:



题目:一个平面迷宫中有一个人,迷宫中有些点起火了,火和人每个单位时间只能向相邻的格子移动,

            其中有一些空间被墙壁占据,问这个人在不背或烧到的情况下,离开迷宫的最快时间。

思路是先用bfs预处理每个格子起火的时间,在来一次bfs走迷宫,入队时判断着火事件和父节点时间大小关系

代码如下:

#include<cstdio>  
#include<cstring>  
#include<cmath>  
#include<cstdlib>  
#include<iostream>  
#include<algorithm>  
#include<vector>  
#include<map>  
#include<queue>  
#include<stack> 
#include<string>
#include<map> 
#include<set>
using namespace std;  
#define LL long long  

const int maxr = 1000 + 5;
const int maxc = 1000 + 5;
const int dirx[] = {-1, 0, 1, 0};
const int diry[] = {0, -1, 0, 1};
const int INF = 100000000;

struct node {
	int x; int y;
};

int G[maxr][maxc], fire_time[maxr][maxc], timeuse[maxr][maxc];
//0表示障碍,1表示空地,2表示着火 


void bfs(int r, int c) {
	queue<node> fire;
	for(int i = 1; i <= r; i++)
		for(int j = 1; j <= c; j++) {
			fire_time[i][j] = INF;
			if(G[i][j] == 2) {
				fire_time[i][j] = 0;
				fire.push((node){i, j});
			}
		}
	
	while(!fire.empty()) {
		node f = fire.front(); fire.pop();
		for(int i = 0; i < 4; i++) {
			int nx = f.x + dirx[i], ny = f.y + diry[i];
			if(nx > 0 && nx <= r && ny > 0 && ny <= c && G[nx][ny] == 1 && fire_time[nx][ny] == INF) {
				fire_time[nx][ny] = fire_time[f.x][f.y] + 1;
				fire.push((node){nx, ny});
			}
		}
	}
} 


void bfs_mg(int jx, int jy, int r, int c) {
	for(int i = 1; i <= r; i++)
		for(int j = 1; j <= c; j++) timeuse[i][j] = INF;
	queue<node> mg;
	timeuse[jx][jy] = 0;
	mg.push((node){jx, jy});
	
	while(!mg.empty()) {
		node u = mg.front(); mg.pop();
		for(int i = 0; i < 4; i++){
			int nx = u.x + dirx[i];
			int ny = u.y + diry[i];
			if(nx > 0 && nx <= r && ny > 0 && ny <= c && G[nx][ny] == 1 && timeuse[nx][ny] == INF && timeuse[u.x][u.y] < fire_time[nx][ny] - 1){
				timeuse[nx][ny] = timeuse[u.x][u.y] + 1;
				mg.push((node){nx, ny});
			}
		}
	}
}

void solve(int r, int c){
	int ans = INF;
	for(int i = 1; i <= r; i++)
		ans = min(ans, timeuse[i][1]);
	for(int i = 1; i <= r; i++)
		ans = min(ans, timeuse[i][c]);
	for(int j = 1; j <= c; j++)
		ans = min(ans, timeuse[1][j]);
	for(int j = 1; j <= c; j++)
		ans = min(ans, timeuse[r][j]);
	if(ans == INF) printf("IMPOSSIBLE\n");
	else printf("%d\n", ans + 1);
}

int main() {
	//freopen("input.txt", "r", stdin);
	int t; scanf("%d", &t);
	while(t--) {
		int r, c; scanf("%d%d", &r, &c);
		int jx, jy;
		for(int i = 1; i <= r; i++) {
			getchar();
			for(int j = 1; j <= c; j++)	{
				char x; scanf("%c", &x);
				if(x == '#') G[i][j] = 0;
				else if(x == '.') G[i][j] = 1;
				else if(x == 'F') G[i][j] = 2;
				else {G[i][j] = 0; jx = i; jy = j;}
			}
		}
		
		bfs(r, c);
		bfs_mg(jx, jy, r, c);
		
		solve(r, c);
		
		//for(int i = 1; i <= r; i++)
		//	for(int j = 1; j <= c; j++) printf("%d ", fire_time[i][j]);
		//for(int i = 1; i <= r; i++)
		//	for(int j = 1; j <= c; j++) printf("%d ", time[i][j]);
		//for(int i = 1; i <= r; i++)
		//	for(int j = 1; j <= c; j++) printf("%d ", G[i][j]);
	}
	return 0;
}








uva 11624 大火蔓延的迷宫 Fire!(两次bfs)

标签:

原文地址:http://blog.csdn.net/u014664226/article/details/45752315

(0)
(0)
   
举报
评论 一句话评论(0
登录后才能评论!
© 2014 mamicode.com 版权所有  联系我们:gaon5@hotmail.com
迷上了代码!