1054: [HAOI2008]移动玩具

  在一个4*4的方框内摆放了若干个相同的玩具,某人想将这些玩具重新摆放成为他心中理想的状态,规定移动
时只能将玩具向上下左右四个方向移动,并且移动的位置不能有玩具,请你用最少的移动次数将初始的玩具状态移
动到某人心中的目标状态。

Input

  前4行表示玩具的初始状态,每行4个数字1或0,1表示方格中放置了玩具,0表示没有放置玩具。接着是一个空
行。接下来4行表示玩具的目标状态,每行4个数字1或0,意义同上。

Output

  一个整数,所需要的最少移动次数。

Sample Input

1111
0000
1110
0010

1010
0101
1010
0101

Sample Output

4
 

分析:

这道题拿到之后第一件想到的事情就是,诶!这是道深搜题诶。而且这个搜索很明显。这道题的数据应该也挺水的所以,就没想什么别的方法

我想的简单粗暴。
1,我们发现,无论怎么移动,如果初始和最终都放了话,那个位置其实不用考虑。因为。就算要移动它,因为它本来就要放哪个位置,那就得找一个新的放在哪个位置。这个过程我们可以想成移动别的点经过了这个位置。
2,因为如果深搜每次只能移动一个点。那么我们就在去完重后对每个初始节点将整张图搜索一遍。将每个遇到对目标节点记录其的步数。这些都放到一个forces [ number ] [ z ] 这里number指的是第几个初始节点 z指的是第几个目标节点。枚举整个图。完成整个表。。为什么我们每次不举最短的那个目标节点。因为。纵观全局,可能会遇到。虽然这个点当前是最近的。但是对别的点来说就没有最近的点。所以我们得考虑全局。当然考虑全局有很多办法。但是我都说了没想什么办法。直接暴力。
3,之后就是组合整个forces数组了,每次每个目标节点只能与一个初始节点匹配。同时还保证综合的步数最小。因为我没这么想(同上)。既然都这么暴力了!那就更暴力一点啊啊啊啊!!!!!!直接用全排列来解决这个问题。

这就是我的黄暴做法。然而所以。就是这样。dalao看到了千万别喷。

#include<cstdio>
#include<algorithm>
#include<string.h>
using namespace std;
int one[5][5],two[5][5],cnt;
int forces[17][17];
int left[4]={1,-1,0,0},right[4]={0,0,1,-1};
int visit[5][5],ans=214748;
int visit_1[20];
struct node{
int x,y,step;
}queue[1001];
void BFS(int x_1,int y_1,int number)
{
memset(visit,0,sizeof(visit));
int head=1,last=1;
node first;
first.x=x_1;first.y=y_1;first.step=0;
queue[1]=first;visit[x_1][y_1]=1;
while(head<=last)
{
node news=queue[head];
for(int i=0;i<4;++i)
{
int x=news.x+left[i],y=news.y+right[i];
if(x>0&&x<=4&&y>0&&y<=4&&(!visit[x][y]))
{
node zz;
zz.x=x;zz.y=y;zz.step=news.step+1;
if(two[x][y]){
forces[number][two[x][y]]=zz.step;
}
queue[++last]=zz;
visit[x][y]=1;
}
}
++head;
}
return ;
}
int lie[20];
void DFS(int x)
{
if(x>cnt)
{
int ans_1=0;
for(int i=1;i<=cnt;++i)
{
ans_1+=forces[i][lie[i]];
}
ans=min(ans,ans_1);
return ;
}
for(int i=1;i<=cnt;i++)
{
if(visit_1[i])continue;
visit_1[i]=1;
lie[x]=i;
DFS(x+1);
visit_1[i]=0;
lie[x]=0;
}
return ;
}
int main()
{
for(int i=1;i<=4;++i)
for(int j=1;j<=4;++j)
scanf("%1d",&one[i][j]);
for(int i=1;i<=4;++i)
for(int j=1;j<=4;++j)
{
scanf("%1d",&two[i][j]);
if(two[i][j]==1&&two[i][j]==one[i][j])
one[i][j]=two[i][j]=0;
else if(two[i][j]==1){
++cnt;
two[i][j]=cnt;
}
}
int cnt_1=0;
for(int i=1;i<=4;i++)
for(int j=1;j<==4;++j)
{
if(one[i][j])
{
++cnt_1;
BFS(i,j,cnt_1);
}
}
DFS(1);
printf("%d",ans);
return 0;
}

嗯。就是这样。我觉得已经够暴力了。。

BZOJ 1054 广搜的更多相关文章

  1. Bzoj 2252: [2010Beijing wc]矩阵距离 广搜

    2252: [2010Beijing wc]矩阵距离 Time Limit: 10 Sec  Memory Limit: 256 MBSubmit: 563  Solved: 274[Submit][ ...

  2. BZOJ 1054 题解

    1054: [HAOI2008]移动玩具 Time Limit: 10 Sec  Memory Limit: 162 MBSubmit: 1888  Solved: 1035[Submit][Stat ...

  3. HDU--杭电--1195--Open the Lock--深搜--都用双向广搜,弱爆了,看题了没?语文没过关吧?暴力深搜难道我会害羞?

    这个题我看了,都是推荐的神马双向广搜,难道这个深搜你们都木有发现?还是特意留个机会给我装逼? Open the Lock Time Limit: 2000/1000 MS (Java/Others)  ...

  4. HDU 5652(二分+广搜)

    题目链接:http://acm.hust.edu.cn/vjudge/contest/128683#problem/E 题目大意:给定一只含有0和1的地图,0代表可以走的格子,1代表不能走的格 子.之 ...

  5. nyoj 613 免费馅饼 广搜

    免费馅饼 时间限制:1000 ms  |  内存限制:65535 KB 难度:3   描述 都说天上不会掉馅饼,但有一天gameboy正走在回家的小径上,忽然天上掉下大把大把的馅饼.说来gameboy ...

  6. poj 3984:迷宫问题(广搜,入门题)

    迷宫问题 Time Limit: 1000MS   Memory Limit: 65536K Total Submissions: 7635   Accepted: 4474 Description ...

  7. poj 3278:Catch That Cow(简单一维广搜)

    Catch That Cow Time Limit: 2000MS   Memory Limit: 65536K Total Submissions: 45648   Accepted: 14310 ...

  8. 双向广搜 POJ 3126 Prime Path

      POJ 3126  Prime Path Time Limit: 1000MS   Memory Limit: 65536K Total Submissions: 16204   Accepted ...

  9. 广搜+打表 POJ 1426 Find The Multiple

    POJ 1426   Find The Multiple Time Limit: 1000MS   Memory Limit: 10000K Total Submissions: 25734   Ac ...

随机推荐

  1. 安装redis监控

    在修改登录中心的时候,数据存储在redis里面,需要对redis进行监控,使用的是Redis-Live 参考文章: http://www.nkrode.com/article/real-time-da ...

  2. Codeforces Round #384 (Div. 2)D - Chloe and pleasant prizes 树形dp

    D - Chloe and pleasant prizes 链接 http://codeforces.com/contest/743/problem/D 题面 Generous sponsors of ...

  3. JSP Servlet性能分析

    JSP Servlet性能分析:http://www.docin.com/p-757790851.html

  4. keil l251 command summary --Lib

    keil l251 command summaryLIB251 LIST MYLIB.LIB TO MYLIB.LST PUBLICS LIB251 EXTRACT MYLIB.LIB (GOODCO ...

  5. 查询修改linux 打开文件句柄数量

    查询系统支持最大可打开文件句柄数量: #vi /proc/sys/fs/file-max 查询当前连接用户最大可打开文件句柄数量: #ulimit -a 修改当前连接用户最大可打开文件句柄数量: #u ...

  6. 译:C#面向对象的基本概念 (Basic C# OOP Concept) 第二部分(封装,抽象,继承)

    6.封装 封装就是对外部类隐藏成员或变量.我已经说过房子的保安仅仅被限制在房子的入口处,不需要知道屋内发生了什么.房主对保安隐藏了屋内所发生的任何事,以便更安全.隐藏和限制就被称为封装. 例如我们有两 ...

  7. Android SDK Manager无法显示可供下载的未安装SDK解决方案

    FAQ: 问下的 我的ANDROID SDK MANAGER里原来下载了一些SDK,但是我现在想重新下载新的SDK,咋Packages列表没显示呢?该怎么办? Answer: 据说dl-ssl.goo ...

  8. Linux下添加硬盘,分区,格式化详解

    2005-10-17 在我们添加硬盘前,首先要了解linux系统下对硬盘和分区的命名方法. 在Linux下对IDE的设备是以hd命名的,第一个ide设备是hda,第二个是hdb.依此类推 我们一般主板 ...

  9. linux 下面 jdk1.7 rpm 包的安装

    1.下载安装jdk7.0 for linux 我下载的版本为:jdk-7u2-linux-i586.rpm 下载地址为:http://www.oracle.com/technetwork/java/j ...

  10. 【转载】linux内核启动android文件系统过程分析

    主要介绍linux 内核启动过程以及挂载android 根文件系统的过程,以及介绍android 源代码中文件系统部分的浅析. 主要源代码目录介绍Makefile (全局的Makefile)bioni ...