【POJ 2049】Finding Nemo

【POJ 2049】Finding Nemo

迷宫类Bfs,不同于之前的是之前是点 这次是房间,我的做法是把每个房间看做一个点(移动地图使房间为整型坐标 便于用数组下表表示房间坐标) 上下左右是墙/门/无用1 0 -1表示 然后Bfs遍历即可 坑点有x/y<0 和x/y > 199的情况 贡献了好多个RE

上代码

#include <cstdio>
#include <cstring>
#include <queue>

using namespace std;

typedef struct Point
{
    int d[4];//0-上 1-下 2-左 3-右
    int st;
}Point;

int dirx[] = { 0, 0,-1, 1};
int diry[] = { 1,-1, 0, 0};
Point mp[233][233];
bool rest[233][233];
bool vis[233][233];
int m,n;

void Init()
{
    memset(rest,0,sizeof(rest));
    memset(vis,0,sizeof(vis));
}

void SetWall()
{
    int x,y,d,t;
    while(m--)
    {
        scanf("%d %d %d %d",&x,&y,&d,&t);
        while(t--)
        {
            if(d)
            {
                ++y;
                mp[x][y].d[3] = 1;
                mp[x+1][y].d[2] = 1;
                if(!rest[x][y])
                {
                    rest[x][y] = 1;
                    mp[x][y].d[2] = mp[x][y].d[0] = mp[x][y].d[1] = -1;
                }
                if(!rest[x+1][y])
                {
                    rest[x+1][y] = 1;
                    mp[x+1][y].d[3] = mp[x+1][y].d[0] = mp[x+1][y].d[1] = -1;
                }
            }
            else
            {
                ++x;
                mp[x][y].d[0] = 1;
                mp[x][y+1].d[1] = 1;
                if(!rest[x][y])
                {
                    rest[x][y] = 1;
                    mp[x][y].d[1] = mp[x][y].d[2] = mp[x][y].d[3] = -1;
                }
                if(!rest[x][y+1])
                {
                    rest[x][y+1] = 1;
                    mp[x][y+1].d[2] = mp[x][y+1].d[0] = mp[x][y+1].d[3] = -1;
                }
            }
        }
    }
}

void SetDoor()
{
    int x,y,d;
    while(n--)
    {
        scanf("%d %d %d",&x,&y,&d);
        if(d)
        {
            mp[x][y+1].d[3] = 0;
            mp[x+1][y+1].d[2] = 0;
        }
        else
        {
            mp[x+1][y].d[0] = 0;
            mp[x+1][y+1].d[1] = 0;
        }
    }
}

int Bfs(int x,int y)
{
    int i,xx,yy;
    mp[x][y].st = 0;
    queue <pair<int,int> >q;
    q.push(pair<int,int> (x,y));
    vis[x][y] = 1;
    if(!rest[x][y]) return 0;
    while(!q.empty())
    {
        x = q.front().first;
        y = q.front().second;
        q.pop();
        for(i = 0; i < 4; ++i)
        {
            xx = x + dirx[i];
            yy = y + diry[i];
            if(mp[x][y].d[i] == -1) return mp[x][y].st;
            else if(!mp[x][y].d[i] &&!vis[xx][yy])
            {
                vis[xx][yy] = 1;
                mp[xx][yy].st = mp[x][y].st+1;
                q.push(pair<int,int> (xx,yy));
            }
        }
    }
    return -1;
}

int main()
{
    //freopen("in.txt","r",stdin);
    double x,y;
    while(~scanf("%d %d",&m,&n) && m != -1)
    {
        Init();
        SetWall();
        SetDoor();
        scanf("%lf %lf",&x,&y);
        if(x < 0|| y < 0 || x > 199 || y > 199 ||(n == 0 && m == 0)) printf("0\n");
        else printf("%d\n",Bfs((int)(x+1),(int)(y+1)));
    }
    return 0;
}
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值