UVA 11624 Fire! 【特殊BFS】

题目链接

题意

人被困在迷宫里,有一些火苗在迷宫中会随时间蔓延,问人能否安全走到迷宫边界

分析

题本身很简单,只是这种题有两种处理方法:

  • 火的状态很简单,只需要知道某个时间某个点有没有火,所以单独BFS一张火的图就可以了
  • 一种比较巧妙的方法是,把火与人都当做BFS中的元素在一个队列中处理,注意BFS中同一层要先处理火,也就是最开始要先把火给入队

AC代码

(当时写的比较仓促,代码很丑……)

//UVA 11624 Fire!
//AC 2016-7-24 22:34:50
//BFS
#include <iostream>
#include <cstdio>
#include <algorithm>
#include <cmath>
#include <cctype>
#include <cstdlib>
#include <cstring>
#include <vector>
#include <set>
#include <string>
#include <map>
#include <queue>
#include <deque>
#include <list>
#include <sstream>
#include <stack>
using namespace std;

#define cls(x) memset(x,0,sizeof x)
#define inf(x) memset(x,0x3f,sizeof x)
#define neg(x) memset(x,-1,sizeof x)
#define ninf(x) memset(x,0xc0,sizeof x)
#define st0(x) memset(x,false,sizeof x)
#define st1(x) memset(x,true,sizeof x)
#define INF 0x3f3f3f3f
#define lowbit(x) x&(-x)
#define bug cout<<"here"<<endl;
//#define debug

int G[1500][1500];
int R,C;
const int dx[]={1,-1,0,0};
const int dy[]={0,0,1,-1};
vector<pair<int,int> > fires;

int fx,fy;

struct node
{
    int x,y;
    int steps;
    bool isfire;
    node(){}
    node(int a,int b,int c):x(a),y(b),steps(c),isfire(0){}
    bool operator< (const node &rhs) const
    {
        if(steps==rhs.steps)
            return !isfire;
        return steps>rhs.steps;
    }
}p,q;

int visit[1500][1500];

int BFS(int sx,int sy)
{
    if(sx==0||sx==R-1||sy==0||sy==C-1)
        return 1;
    inf(visit);
    priority_queue<node> que;
    for(int i=0;i<fires.size();++i)
    {
        node p(fires[i].first,fires[i].second,0);
        p.isfire=1;
        que.push(p);
    }
    que.push(node(sx,sy,0));
    while(que.size())
    {
        p=que.top();
        //cout<<p.x<<"--"<<p.y<<"--"<<p.steps<<endl;
        que.pop();
        if(p.isfire)
        {
            if(G[p.x][p.y]<p.steps)
                continue;
            else
                G[p.x][p.y]=p.steps;
            for(int i=0;i<4;++i)
            {
                q.x=p.x+dx[i];
                q.y=p.y+dy[i];
                q.steps=p.steps+1;
                q.isfire=1;
                if(q.x>=0&&q.x<R&&q.y>=0&&q.y<C&&G[q.x][q.y]>q.steps)
                {
                    G[q.x][q.y]=q.steps;
                    que.push(q);
                }
            }
            continue;
        }
        if(visit[p.x][p.y]<p.steps)
            continue;
        if(p.x==0||p.x==R-1||p.y==0||p.y==C-1)
            return p.steps+1;
        for(int i=0;i<4;++i)
        {
            q.x=p.x+dx[i];
            q.y=p.y+dy[i];
            q.steps=p.steps+1;
            q.isfire=0;
            if(q.x>=0&&q.y>=0&&q.x<R&&q.y<C&&q.steps<visit[q.x][q.y]&&q.steps<G[q.x][q.y])
            {
                visit[q.x][q.y]=q.steps;
                que.push(q);
            }
        }
    }
    return -1;
}

int main()
{
    #ifdef debug
        freopen("E:\Documents\code\input.txt","r",stdin);
        freopen("E:\Documents\code\output.txt","w",stdout);
    #endif
    int T=0;
    scanf("%d",&T);
    char c;
    while(T--)
    {
        scanf("%d %d",&R,&C);
        getchar();
        inf(G);
        int sx,sy;
        fires.clear();
        for(int i=0;i<R;++i)
        {
            for(int j=0;j<C;++j)
            {
                c=getchar();
                if(c=='#')
                    G[i][j]=-1;
                else if(c=='F')
                {
                    G[i][j]=1;
                    fires.push_back(make_pair(i,j));
                }
                else
                {
                    G[i][j]=INF;
                    if(c=='J')
                    {
                        sx=i;sy=j;
                    }
                }
            }
            getchar();
        }
        int res=BFS(sx,sy);
        if(res==-1)
            printf("IMPOSSIBLE
");
        else
            printf("%d
",res);
    }
    return 0;
}
原文地址:https://www.cnblogs.com/DrCarlluo/p/6580609.html