HDU 1448(The Treasure)

#include <cstdio>
#include <queue>
#include <cstring>
#include <algorithm>
using namespace std;
const int MAXN = 105;

struct monster //怪物
{
    int agg; //是否有攻击性
    int num; //位置数量
    int x[105]; //位置横坐标
    int y[105]; //位置纵坐标
}mon[MAXN];

struct node //结点
{
    int x, y;
    node() {}
    node(int x, int y) : x(x), y(y) {}
};

char mp[MAXN][MAXN]; //地图
char mp2[MAXN][MAXN]; //修改前地图
bool vis[MAXN][MAXN][MAXN]; //访问情况
int n, m; //地图边长
int p, maxNum; //怪物的数量,怪物的最大位置数量
int sx, sy; //起点位置
int ex, ey; //终点位置
int dir[8][2] = { {0,1},{-1,1},{-1,0},{-1,-1},{0,-1},{1,-1},{1,0},{1,1} }; //前进方向

bool judge(int x, int y)
{
    return x <= 0 || x > n || y <= 0 || y > m || mp[x][y] == '#';
}

bool judge2(int x, int y)
{
    return x <= 0 || x > n || y <= 0 || y > m || mp2[x][y] == '#';
}

//将怪物的格子及其周边的格子(攻击性)填充为'#'
void fill(int t)
{
    int step;
    for (int i = 0; i < p; i++)
    {
        step = t % mon[i].num;
        mp[mon[i].x[step]][mon[i].y[step]] = '#';
        if (mon[i].agg == 1)
        {
            int x, y;
            for (int j = 0; j < 8; j++)
            {
                x = mon[i].x[step] + dir[j][0];
                y = mon[i].y[step] + dir[j][1];
                if (judge2(x, y))
                    continue;
                mp[x][y] = '#';
            }
        }
    }
}

//将怪物的格子及其周边的格子(攻击性)恢复为'.'
void restore(int t)
{
    int step;
    for (int i = 0; i < p; i++)
    {
        step = t % mon[i].num;
        mp[mon[i].x[step]][mon[i].y[step]] = '.';
        if (mon[i].agg == 1)
        {
            int x, y;
            for (int j = 0; j < 8; j++)
            {
                x = mon[i].x[step] + dir[j][0];
                y = mon[i].y[step] + dir[j][1];
                if (judge2(x, y))
                    continue;
                mp[x][y] = '.';
            }
        }
    }
}

int BFS()
{
    memset(vis, false, sizeof(vis));
    queue<node> q;
    q.push(node(sx, sy));

    int x, y, t;
    int ret = 0;
    while (1)
    {
        int sz = q.size();
        if (sz == 0)
            break;
        ++ret;

        t = ret % maxNum;
        fill(t);

        node now;
        while (sz--)
        {
            now = q.front();
            q.pop();

            if (mp[now.x][now.y] == '#')
                continue;

            if (!vis[now.x][now.y][t])
            {
                vis[now.x][now.y][t] = true;
                q.push(now);
            }
            for (int i = 0; i < 8; i++)
            {
                x = now.x + dir[i][0];
                y = now.y + dir[i][1];

                if (judge(x, y))
                    continue;
                if (x == ex && y == ey)
                    return ret;

                if (!vis[x][y][t])
                {
                    vis[x][y][t] = true;
                    q.push(node(x, y));
                }

                x += dir[i][0];
                y += dir[i][1];
                if (judge(x, y))
                    continue;

                if (x == ex && y == ey)
                    return ret;

                if (!vis[x][y][t])
                {
                    vis[x][y][t] = true;
                    q.push(node(x, y));
                }
            }
        }
        restore(t);
    }
    return -1;
}

int main()
{
    int Case = 0;
    while (scanf("%d%d", &n, &m) != EOF)
    {
        if (n == 0 && m == 0)
            break;

        for (int i = 1; i <= n; i++) //输入地图
        {
            scanf("%s", mp[i] + 1);
            for (int j = 1; j <= m; j++)
            {
                if (mp[i][j] == 'p') //起点
                {
                    sx = i;
                    sy = j;
                    mp[i][j] = '.';
                }
                else if (mp[i][j] == 't') //终点
                {
                    ex = i;
                    ey = j;
                    mp[i][j] = '.';
                }
            }
        }
        
        memcpy(mp2, mp, sizeof(mp2));

        scanf("%d", &p);
        maxNum = 1;
        for (int i = 0; i < p; i++)
        {
            scanf("%d", &mon[i].num);
            maxNum = max(maxNum, mon[i].num);
            
            for (int j = 0; j < mon[i].num; j++)
                scanf("%d%d", &mon[i].x[j], &mon[i].y[j]);

            if(mp[mon[i].x[0]][mon[i].y[0]] == 'a')
                mon[i].agg = 1;
            else
                mon[i].agg = 0;

            mp[mon[i].x[0]][mon[i].y[0]] = '.';
        }

        if (Case++)
            printf("\n");
        int ans = BFS();
        if (ans == -1)
            printf("impossible\n");
        else
            printf("%d\n", ans);
    }
    return 0;
}
发布了326 篇原创文章 · 获赞 1 · 访问量 1万+

猜你喜欢

转载自blog.csdn.net/Intelligence1028/article/details/105378918
今日推荐