• hdu4528 小明系列故事——捉迷藏(记录状态的BFS)题解


    思路:

    一道BFS题,和以前的BFS有点不同,这里的vis数组需要记录每次走时的状态,所以开了3维,只对该状态下的vis修改。

    注意坑点:S的位置是可以走的

    代码:

    #include<queue>
    #include<cstdio>
    #define ll long long
    using namespace std;
    const int N = 100+5;
    char mp[N][N];
    bool vis[4][N][N];
    int X1,Y1,X2,Y2,x,y,n,m,t,to[4][2] = {0,1,0,-1,1,0,-1,0},cnt = 1;
    struct node{
        int x,y;
        int step;
        int Find;
    };
    void update(node &a){
        if(a.x == X1 && a.Find != 1){   //等于1不改变状态
            int s = min(a.y,Y1) + 1;
            int e = max(a.y,Y1) - 1;
            int flag = 1;
            for(int i = s;i <= e;i++){
                if(mp[X1][i] != '.'){
                    flag = 0;
                    break;
                }
            }
            if(flag) a.Find = (a.Find == 0? 1 : 3);
        }
        if(a.x == X2 && a.Find != 2){
            int s = min(a.y,Y2) + 1;
            int e = max(a.y,Y2) - 1;
            int flag = 1;
            for(int i = s;i <= e;i++){
                if(mp[X2][i] != '.'){
                    flag = 0;
                    break;
                }
            }
            if(flag) a.Find = (a.Find == 0? 2 : 3);
        }
        if(a.y == Y1 && a.Find != 1){
            int s = min(a.x,X1) + 1;
            int e = max(a.x,X1) - 1;
            int flag = 1;
            for(int i = s;i <= e;i++){
                if(mp[i][Y1] != '.'){
                    flag = 0;
                    break;
                }
            }
            if(flag) a.Find = (a.Find == 0? 1 : 3);
        }
        if(a.y == Y2 && a.Find != 2){
            int s = min(a.x,X2) + 1;
            int e = max(a.x,X2) - 1;
            int flag = 1;
            for(int i = s;i <= e;i++){
                if(mp[i][Y2] != '.'){
                    flag = 0;
                    break;
                }
            }
            if(flag) a.Find = (a.Find == 0? 2 : 3);
        }
    }
    void BFS(){
        queue<node> q;
        while(!q.empty()) q.pop();
        node a,b;
        a.x = x,a.y = y,a.Find = 0,a.step = 0;
        update(a);
        q.push(a);
        while(!q.empty()){
            a = q.front();q.pop();
            if(a.Find == 3 && a.step <= t){
                printf("Case %d:
    %d
    ",cnt++,a.step);
                return;
            }
            for(int i = 0;i < 4;i++){
                b.x = a.x + to[i][0];
                b.y = a.y + to[i][1];
                if(b.x < 1 || b.y < 1 || b.x > n || b.y > m) continue;
                if(mp[b.x][b.y] != '.') continue;
                b.Find = a.Find;
                update(b);
                if(vis[b.Find][b.x][b.y]) continue;
                vis[b.Find][b.x][b.y] = true;
                b.step = a.step + 1;
                q.push(b);
            }
        }
        printf("Case %d:
    -1
    ",cnt++);
    }
    int main(){
        int T;
        scanf("%d",&T);
        while(T--){
            scanf("%d%d%d",&n,&m,&t);
            for(int i = 1;i <= n;i++){
                scanf("%s",mp[i] + 1);
                for(int j = 1;j <= m;j++){
                    if(mp[i][j] == 'D') X1 = i,Y1 = j;
                    else if(mp[i][j] == 'E') X2 = i,Y2 = j;
                    else if(mp[i][j] == 'S') x = i,y = j,mp[i][j] = '.';
                }
            }
            memset(vis,0,sizeof(vis));
            BFS();
        }
        return 0;
    }
    


  • 相关阅读:
    8) linux安装samba服务器
    7) k8s获取apiversion下面的对应可用资源
    4) cobbler自动安装linux
    3) KVM命令--使用篇(1)
    2) 各种开源环境自动部署脚本
    1) nginx编译安装
    扁平式小清新导航
    互联网公司常用水平导航(二级导航)
    水平导航-三级导航-切换流畅
    简约蓝色系导航(三级导航)
  • 原文地址:https://www.cnblogs.com/KirinSB/p/9408796.html
Copyright © 2020-2023  润新知