推箱子

Time Limit: 2000/1000 MS (Java/Others)    Memory Limit: 65536/32768 K (Java/Others)

Total Submission(s): 6758    Accepted Submission(s): 1906

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
 
Author
Ignatius.L & weigang Lee

感觉还是有难度的,刚开始的时候没考虑人所在的位置,这里有一个坑,箱子移动的时候人必须在箱子后边,这样才可以推到箱子,这样的话就会有点复杂,每次推箱子的时候我们都应该判断一下,上一次人所在的位置是否可以到达这次推箱子的位置,所以这就不只是一个bfs可以搞定的了,在结构体中我们记录的应该有箱子和人的位置以及当前步数,每一次位置变换都应该更新人还有箱子的位置,同时判定该方案的可行性(加上了注释就CE了,不知道是什么鬼)
#include<stdio.h>
#include<cstring>
#include<queue>
#include<iostream>
#include<algorithm>
using namespace std;
int dx[4]={0,0,1,-1};
int dy[4]={1,-1,0,0};
int map[10][10],mark[10][10][10][10];
int n,m,flag,markk[10][10];
int xiangx,xiangy;
struct dian
{
int x,y;
int renx,reny;
int step;
}st,end;
struct ren
{
int x,y;
}vv,stt;
int bffs(ren stt)
{
queue<ren>q;
markk[stt.x][stt.y]=1;
q.push(stt);
ren v,vn;
while(!q.empty())
{
vn=q.front();
q.pop();
if(vn.x==vv.x&&vn.y==vv.y)
return 1;//可以到达现在推箱子的位置
for(int i=0;i<4;i++)
{
v.x=vn.x+dx[i];
v.y=vn.y+dy[i];
if(v.x>=n||v.x<0||v.y>=m||v.y<0)
continue;//不能出界
if(map[v.x][v.y]==1) continue;
if(v.x==xiangx&&v.y==xiangy) continue;
//不能在以前箱子所在的位置
if(markk[v.x][v.y]) continue;
markk[v.x][v.y]=1;
q.push(v);
}
}
return 0;
}
void bfs(dian st)
{
queue<dian>p;
p.push(st);//使用人还有箱子的位置实现四维标记
mark[st.x][st.y][st.renx][st.reny]=1;
dian v,vn;
while(!p.empty())
{
vn=p.front();
p.pop();
if(vn.x==end.x&&vn.y==end.y)
{//如果现在箱子被推到了指定的位置
flag=1;
printf("%d\n",vn.step);
return;
}
for(int i=0;i<4;i++)
{//箱子位置变更
v.x=vn.x+dx[i];
v.y=vn.y+dy[i];
v.step=vn.step+1;
v.renx=vn.x;
v.reny=vn.y;
vv.x=vn.x-dx[i];//vv中的x,y存储了推箱子时人应该在的位置
vv.y=vn.y-dy[i];
if(v.x>=n||v.x<0||v.y>=m||v.y<0) continue;
if(map[v.x][v.y]==1) continue;
if(map[vv.x][vv.y]==1||vv.x>=n||vv.x<0||vv.y>=m||vv.y<0) continue;
if(mark[v.x][v.y][v.renx][v.reny]) continue;
stt.x=vn.renx;//结构体中存放的有当时人的位置
stt.y=vn.reny;
xiangx=vn.x;
xiangy=vn.y;
memset(markk,0,sizeof(markk));
if(!bffs(stt)) continue;//箱子被推之前的位置,因为还要判定是否可以推
mark[v.x][v.y][v.renx][v.reny]=1;
p.push(v);
}
}
}
int main()
{
int T;
scanf("%d",&T);
while(T--)
{
flag=0;
scanf("%d%d",&n,&m);
for(int i=0;i<n;i++)
for(int j=0;j<m;j++)
{
scanf("%d",&map[i][j]);
if(map[i][j]==2)
{
st.x=i;
st.y=j;
xiangx=i;
xiangy=j;
}
if(map[i][j]==3)
{
end.x=i;
end.y=j;
}
if(map[i][j]==4)
{
st.renx=i;
st.reny=j;
}
}
st.step=0;
memset(mark,0,sizeof(mark));
memset(markk,0,sizeof(markk));
bfs(st);
if(!flag) printf("-1\n");
}
return 0;
}

hdoj--1254--推箱子(bfs好题)的更多相关文章

  1. HDU 1254 推箱子 BFS

    题目链接 http://acm.hdu.edu.cn/showproblem.php?pid=1254 题目分析: 做这道题,感觉挺简单的,做着做着就错了20次, 我也是醉了, WA到吐的节奏啊! 思 ...

  2. hdu - 1254 推箱子 (bfs+bfs)

    http://acm.hdu.edu.cn/showproblem.php?pid=1254 题目意思很简单,只要思路对就好. 首先考虑搬运工能否到达推箱子的那个点,这个可以根据箱子前进方向得出搬运工 ...

  3. hdu.1254.推箱子(bfs + 优先队列)

    推箱子 Time Limit: 2000/1000 MS (Java/Others)    Memory Limit: 65536/32768 K (Java/Others) Total Submis ...

  4. HDU 1254 推箱子(BFS加优先队列)

    传送门: http://acm.hdu.edu.cn/showproblem.php?pid=1254 推箱子 Time Limit: 2000/1000 MS (Java/Others)    Me ...

  5. hdu 1254 推箱子(嵌套搜索,bfs中有dfs)

    推箱子 Time Limit: 2000/1000 MS (Java/Others)    Memory Limit: 65536/32768 K (Java/Others)Total Submiss ...

  6. HDU 1254 推箱子(BFS)

    Problem Description 推箱子是一个很经典的游戏.今天我们来玩一个简单版本.在一个M*N的房间里有一个箱子和一个搬运工,搬运工的工作就是把箱子推到指定的位置,注意,搬运工只能推箱子而不 ...

  7. hdu 1254 推箱子(双重bfs)

    题目链接 Problem Description 推箱子是一个很经典的游戏.今天我们来玩一个简单版本.在一个M*N的房间里有一个箱子和一个搬运工,搬运工的工作就是把箱子推到指定的位置,注意,搬运工只能 ...

  8. [HDU 1254] 推箱子

    推箱子 Time Limit: 2000/1000 MS (Java/Others)    Memory Limit: 65536/32768 K (Java/Others) Total Submis ...

  9. hdu 1254 推箱子(搜索)

    我写的第一道感觉比较难的搜索 题目链接:http://acm.hdu.edu.cn/showproblem.php?pid=1254 首先要推箱子的话要满足人能够在箱子旁边,而且人的对面也是可通的. ...

  10. 推箱子 BFS

    [编程题] 推箱子 大家一定玩过“推箱子”这个经典的游戏.具体规则就是在一个N*M的地图上,有1个玩家.1个箱子.1个目的地以及若干障碍,其余是空地.玩家可以往上下左右4个方向移动,但是不能移动出地图 ...

随机推荐

  1. mybatis中<![CDATA[]]>的作用

    此篇文章引自QH_JAVA的文章 在使用mybatis 时我们sql是写在xml 映射文件中,如果写的sql中有一些特殊的字符的话,在解析xml文件的时候会被转义,但我们不希望他被转义,所以我们要使用 ...

  2. 关于latch: cache buffers chains的sql优化

    前段时间,优化了一些耗buffer比较多的sql,但是CPU使用率还是没下来 . 查看操作系统CPU使用率 查看awr,发现又有一条超级耗性能的sql冒出来了. 该SQL每次执行耗费3e多个buffe ...

  3. PHP:获取用户IP

    文章来源:http://www.cnblogs.com/hello-tl/p/7685263.html //获取用户ip(外网ip 服务器上可以获取用户外网Ip 本机ip地址只能获取127.0.0.1 ...

  4. 十款开发者常用的Chrome插件,让chrome成为开发利器!

    Chrome浏览器无论是作为浏览器市场的NO1还是其强大的跨平台能力以及丰富的扩展插件,一直是许多开发者的首要选择的浏览器.chrome浏览器也因为其丰富的Chrome插件,帮助开发者们在开发流程中极 ...

  5. super在python中有什么用

    所属网站分类: python高级 > 面向对象 作者:阿里妈妈 链接:http://www.pythonheidong.com/blog/article/74/ 来源:python黑洞网 有什么 ...

  6. Spring 事物注解属性

    @Transactional属性 . propagation 事物的传播属性 . isolation 事物的隔离属性 . readonly 设置只读属性 . timeout 设置超时属性 . roll ...

  7. Analyzer原理

    [常用分词器] SimpleAnalyzer StopAnalyzer WhitespaceAnalyzer StandardAnalyze [TokenStream] she is a studen ...

  8. Bone Collector II(hdu 2639)

    题意:求01背包的第k最优值 输入:第一行为T,下面是T组数据,每组数据有n,m,k 代表n件物品,m容量,和题目要求的k,下一行是n个物品的价值,再一行是n个物品的体积 输出:T行答案 /* 类似于 ...

  9. 【存储过程】MySQL存储过程/存储过程与自定义函数的区别

    ---------------------------存储过程-------------------- 语法: 创建存储过程: CREATE [definer = {user|current_user ...

  10. 【git】Git 提示fatal: remote origin already exists 错误解决办法

    今天使用git 添加远程github仓库的时候提示错误:fatal: remote origin already exists. 最后找到解决办法如下: 1.先删除远程 Git 仓库 $ git re ...