uva11624 - Fire! 两次bfs

题目链接

Problem B: Fire!

Joe works in a maze. Unfortunately, portions of the maze have caught on fire, and
the owner of the maze neglected to create a fire escape plan. Help Joe escape the maze.

Given Joe‘s location in the maze and which squares of the maze are on fire, you must determine whether Joe can exit the maze before the fire reaches him, and how fast he can do it.

Joe and the fire each move one square per minute, vertically or horizontally (not diagonally). The fire spreads all four directions from each square that is on fire. Joe may exit the maze from any square that borders
the edge of the maze. Neither Joe nor the fire may enter a square that is occupied by a wall.

Input Specification

The first line of input contains a single integer, the number of test cases to follow. The first line of each test case contains the two integers R and C,
separated by spaces, with 1 <= R,C <=
1000. The following R lines of the test case each contain one row of the maze. Each of these lines contains exactly C characters,
and each of these characters is one of:

  • #, a wall
  • ., a passable square
  • J, Joe‘s initial position in the maze, which is a passable square
  • F, a square that is on fire

There will be exactly one J in each test case.

Sample Input

2
4 4
####
#JF#
#..#
#..#
3 3
###
#J.
#.F

Output Specification

For each test case, output a single line containing IMPOSSIBLE if Joe cannot exit the maze before the fire reaches him, or an integer giving the
earliest time Joe can safely exit the maze, in minutes.

Output for Sample Input

3
IMPOSSIBLE

Malcolm Sharpe, Ond?ej Lhoták

题目大意:一个平面迷宫中有一个人,迷宫中有些点起火了,火和人每个单位时间只能向相邻的格子移动,其中有一些空间被墙壁占据,问这个人在不背或烧到的情况下,离开迷宫的最快时间。

题解:两次bfs,先bfs出每个地方着火的时间,再bfs人走出迷宫的时间。注意有的地方火不能到达但人是可以走的。

/**
 * @author neko01
 */
//#pragma comment(linker, "/STACK:102400000,102400000")
#include <cstdio>
#include <cstring>
#include <string.h>
#include <iostream>
#include <algorithm>
#include <queue>
#include <vector>
#include <cmath>
#include <set>
#include <map>
using namespace std;
typedef long long LL;
#define min3(a,b,c) min(a,min(b,c))
#define max3(a,b,c) max(a,max(b,c))
#define pb push_back
#define mp(a,b) make_pair(a,b)
#define clr(a) memset(a,0,sizeof a)
#define clr1(a) memset(a,-1,sizeof a)
#define dbg(a) printf("%d\n",a)
typedef pair<int,int> pp;
const double eps=1e-9;
const double pi=acos(-1.0);
const int INF=0x3f3f3f3f;
const LL inf=(((LL)1)<<61)+5;
const int N=1005;
int f[N][N];
bool vis[N][N];
char s[N][N];
int r,c,sx,sy;
struct node{
    int x,y,t;
    node(int x=0,int y=0,int t=0):x(x),y(y),t(t){}
};
int dir[4][2]={-1,0,1,0,0,-1,0,1};
bool immap(int x,int y)
{
    return x>=0&&y>=0&&x<r&&y<c&&!vis[x][y]&&s[x][y]!='#';
}
int bfs()
{
    queue<node>q;
    clr(vis);
    q.push(node(sx,sy,0));
    vis[sx][sy]=true;
    while(!q.empty())
    {
        node cur=q.front();
        int x=cur.x,y=cur.y;
        if(x==0||y==0||x==r-1||y==c-1)
            return cur.t+1;
        q.pop();
        for(int i=0;i<4;i++)
        {
            int xx=x+dir[i][0];
            int yy=y+dir[i][1];
            if(immap(xx,yy))
            {
                if(cur.t+1<f[xx][yy]||f[xx][yy]==-1)
                {
                    vis[xx][yy]=true;
                    q.push(node(xx,yy,cur.t+1));
                }
            }
        }
    }
    return -1;
}
int main()
{
    int t;
    scanf("%d",&t);
    while(t--)
    {
        queue<node>q;
        scanf("%d%d",&r,&c);
        clr1(f);
        for(int i=0;i<r;i++)
        {
            scanf("%s",s[i]);
            for(int j=0;j<c;j++)
            {
                vis[i][j]=false;
                if(s[i][j]=='J')
                    sx=i,sy=j;
                if(s[i][j]=='F')
                {
                    f[i][j]=0;
                    q.push(node(i,j,0));
                    vis[i][j]=true;
                }
            }
        }
        while(!q.empty())
        {
            node cur=q.front();
            int x=cur.x,y=cur.y;
            q.pop();
            for(int i=0;i<4;i++)
            {
                int xx=x+dir[i][0];
                int yy=y+dir[i][1];
                if(immap(xx,yy))
                {
                    f[xx][yy]=f[x][y]+1;
                    q.push(node(xx,yy,cur.t+1));
                    vis[xx][yy]=true;
                }
            }
        }
        int ans=bfs();
        if(ans==-1) puts("IMPOSSIBLE");
        else printf("%d\n",ans);
    }
    return 0;
}
时间: 2024-08-02 22:57:54

uva11624 - Fire! 两次bfs的相关文章

求树的直径【两遍BFS】

两遍BFS.从任意一个点出发,第一遍可以找到直径的一端,从这端出发即可找到另外一端. 证明:从U点出发,到达V[画个图便清晰了] 1.如果U在直径上,则V一定是直径的一个端点. 2.如果U不在直径上.U,V线一定和直径有交点(如果没有交点,从U引一条路到直径交于U'.[反证]).有交点则V一定是直径另一端. 代码:[举例] int path(int x){ //从x出发,求直径 mem(vis,-1); while(!Q.empty()) Q.pop(); Q.push(x); vis[x]=0

URAL 1145. Rope in the Labyrinth(两次BFS啊 )

题目链接:http://acm.timus.ru/problem.aspx?space=1&num=1145 1145. Rope in the Labyrinth Time limit: 0.5 second Memory limit: 64 MB A labyrinth with rectangular form and size m × n is divided into square cells with sides' length 1 by lines that are paralle

UVa 1599 Ideal Path (两次BFS)

题意:给出n个点,m条边的无向图,每条边有一种颜色,求从结点1到结点n颜色字典序最小的最短路径. 析:首先这是一个最短路径问题,应该是BFS,因为要保证是路径最短,还要考虑字典序,感觉挺麻烦的,并不好做,事实用两次BFS, 第一次是倒序BFS,目的是得到从结点 i 到结点n的最短距离,然后再从第一个点开始到最后一个,要保证在查找时,每经过一点要让d值恰好减少1, 直到终点,这也是一个BFS,因为这个字典序在某个结点是一样的,所以是两个BFS,我超时了好几次,因为少写了一个vis, 一定要细心,

hihocoder#1050 : 树中的最长路(树中最长路算法 两次BFS找根节点求最长+BFS标记路径长度+bfs不容易超时,用dfs做TLE了)

#1050 : 树中的最长路 时间限制:10000ms 单点时限:1000ms 内存限制:256MB 描述 上回说到,小Ho得到了一棵二叉树玩具,这个玩具是由小球和木棍连接起来的,而在拆拼它的过程中,小Ho发现他不仅仅可以拼凑成一棵二叉树!还可以拼凑成一棵多叉树——好吧,其实就是更为平常的树而已. 但是不管怎么说,小Ho喜爱的玩具又升级换代了,于是他更加爱不释手(其实说起来小球和木棍有什么好玩的是吧= =).小Ho手中的这棵玩具树现在由N个小球和N-1根木棍拼凑而成,这N个小球都被小Ho标上了不

hdu-2612 两次bfs

http://acm.hdu.edu.cn/showproblem.php?pid=2612 两次bfs, 记录到每个KFC的最短时间.选取最短时间. #include <stdio.h> #include <iostream> #include <string> #include <cstring> #include <cmath> #include <cstdlib> #include <algorithm> #inc

FZU 2196 Escape (两次BFS)

[题目链接]:click here~~ [题目大意]: Description 小明进入地下迷宫寻找宝藏,找到宝藏后却发生地震,迷宫各处产生岩浆,小明急忙向出口处逃跑.如果丢下宝藏,小明就能迅速离开迷宫,但小明并不想轻易放弃自己的辛苦所得.所以他急忙联系当程序员的朋友你(当然是用手机联系),并告诉你他所面临的情况,希望你能告诉他是否能成功带着宝藏逃脱. Input 有多组测试数据. 每组测试数据第一行是一个整数T,代表接下去的例子数.(0<=T<=10) 接下来是T组例子. 每组例子第一行是两

逆向+两次bfs(UVA 1599)

为什么都说简单好想咧.坦白从宽看了人家的代码,涨了好多姿势,, http://blog.csdn.net/u013382399/article/details/38227917 被一个细节坑了.. 2147483647是0x7fffffff啊啊啊,7个f!!! 1 #include <iostream> 2 #include <sstream> 3 #include <cstdio> 4 #include <cstring> 5 #include <c

POJ 3170 Knights of Ni(两次BFS啊)

题目链接:http://poj.org/problem?id=3170 Description Bessie is in Camelot and has encountered a sticky situation: she needs to pass through the forest that is guarded by the Knights of Ni. In order to pass through safely, the Knights have demanded that sh

Find a way(两个BFS)

Problem Description Pass a year learning in Hangzhou, yifenfei arrival hometown Ningbo at finally. Leave Ningbo one year, yifenfei have many people to meet. Especially a good friend Merceki. Yifenfei’s home is at the countryside, but Merceki’s home i