zoukankan      html  css  js  c++  java
  • hdu 1254 推箱子

    推箱子

    Time Limit : 2000/1000ms (Java/Other)   Memory Limit : 65536/32768K (Java/Other)
    Total Submission(s) : 122   Accepted Submission(s) : 47

    Font: Times New Roman | Verdana | Georgia

    Font Size: ← →

    Problem Description

    推箱子是一个很经典的游戏.今天我们来玩一个简单版本.在一个M*N的房间里有一个箱子和一个搬运工,搬运工的工作就是把箱子推到指定的位置,注意,搬运工只能推箱子而不能拉箱子,因此如果箱子被推到一个角上(如图2)那么箱子就不能再被移动了,如果箱子被推到一面墙上,那么箱子只能沿着墙移动.

    现在给定房间的结构,箱子的位置,搬运工的位置和箱子要被推去的位置,请你计算出搬运工至少要推动箱子多少格.

    Input

    输入数据的第一行是一个整数T(1<=T<=20),代表测试数据的数量.然后是T组测试数据,每组测试数据的第一行是两个正整数M,N(2<=M,N<=7),代表房间的大小,然后是一个M行N列的矩阵,代表房间的布局,其中0代表空的地板,1代表墙,2代表箱子的起始位置,3代表箱子要被推去的位置,4代表搬运工的起始位置.

    Output

    对于每组测试数据,输出搬运工最少需要推动箱子多少格才能帮箱子推到指定位置,如果不能推到指定位置则输出-1.

    Sample Input

    1
    5 5
    0 3 0 0 0
    1 0 1 4 0
    0 0 1 0 0
    1 0 2 0 0
    0 0 0 0 0
    

    Sample Output

    4

    #include <iostream>
    #include <cstring>
    #include <algorithm>
    #include <queue>
    using namespace std;
    int dir[4][2]={-1,0,0,1,0,-1,1,0};
    int a[10][10];
    int v[10][10][10][10];
    int m,n;
    struct node
    {
        int bx,by;
        int rx,ry;
        int cnt;
    };
    struct man
    {
        int x,y;
    };
    bool safe(int x,int y)
    {
        if(x<1||y<1||x>n||y>m||a[x][y]==1) return 0;
        return 1;
    }
    
    int bfs2(int si,int sj,int di,int dj,int bi,int bj)
    {
        int v[10][10];
        memset(v,0,sizeof(v));
        queue<man> qu;//新定义了q,所以不用初始化qu了
        man st,sd;
        st.x=si;st.y=sj;
        v[si][sj]=1;
        qu.push(st);
        while(!qu.empty())
        {
            st=qu.front();qu.pop();
            if(st.x==di&&st.y==dj) return 1;
            for(int i=0;i<4;i++)
            {
                sd.x=st.x+dir[i][0];
                sd.y=st.y+dir[i][1];
                if(safe(sd.x,sd.y)&&!v[sd.x][sd.y]&&(sd.x!=bi||sd.y!=bj))
                {
                    v[sd.x][sd.y]=1;
                    qu.push(sd);
                }
            }
        }
        return 0;
    }
    
    
    
    
    
    int bfs(int bi,int bj,int ri,int rj,int di,int dj)
    {
        int i;
        queue<node>q;
        node f,d;
        f.bx=bi;
        f.by=bj;
        f.rx=ri;
        f.ry=rj;
        f.cnt=0;
        v[bi][bj][ri][rj]=1;
        q.push(f);
        while(!q.empty())
        {
            f=q.front();q.pop();
            if(f.bx==di&&f.by==dj)  return f.cnt;
            for(i=0;i<4;i++)
            {
             d.bx = f.bx + dir[i][0];  
                d.by = f.by + dir[i][1];  
                d.rx = f.bx - dir[i][0];  
                    d.ry = f.by - dir[i][1];  
                if(safe(d.bx,d.by)&&safe(d.rx,d.ry)&&!v[d.bx][d.by][d.rx][d.ry])
                {
                    if(bfs2(f.rx,f.ry,d.rx,d.ry,f.bx,f.by))//bfs人能不能走到箱子后面
                    {
                        v[d.bx][d.by][d.rx][d.ry]=1;
                        d.cnt=f.cnt+1;
                        q.push(d);
                    }
                }
            }
        }
        return -1;
    }
    
    
    
    
    
    int main()
    {
        int T,ri,rj,di,dj,bi,bj;
        int i,j;
        cin>>T;
        while(T--)
        {
            cin>>n>>m;
            for(i=1;i<=n;i++)
            {
                for(j=1;j<=m;j++)
                {
                    cin>>a[i][j];
                    if(a[i][j]==4)
                    {
                        ri=i;rj=j;
                    }
                    if(a[i][j]==2)
                    {
                        bi=i;bj=j;
                    }
                    if(a[i][j]==3)
                    {
                        di=i;dj=j;
                    }
                }
            }
            int ans=bfs(bi,bj,ri,rj,di,dj);
            memset(v,0,sizeof(v));
            cout<<ans<<endl;
        }
        return 0;
    }
  • 相关阅读:
    判断ArryaList有没有重复对象的方法
    使用Java对字符串进行升序排序
    用三层盒子结构实现多边框
    盒子模型的margin负数用法
    解决盒子浮动时margin会显示两倍的美观问题
    纯HTML和CSS实现JD轮播图
    Java的策略模式
    Java的适配器模式
    Java的单例模式
    阿里云服务器配置
  • 原文地址:https://www.cnblogs.com/caiyishuai/p/13271283.html
Copyright © 2011-2022 走看看