bzoj 1054: [HAOI2008]移动玩具
Submit: 2574 Solved: 1438
[Submit][Status][Discuss]
Description
在一个4*4的方框内摆放了若干个相同的玩具,某人想将这些玩具重新摆放成为他心中理想的状态,规定移动
时只能将玩具向上下左右四个方向移动,并且移动的位置不能有玩具,请你用最少的移动次数将初始的玩具状态移
动到某人心中的目标状态。
Input
前4行表示玩具的初始状态,每行4个数字1或0,1表示方格中放置了玩具,0表示没有放置玩具。接着是一个空
行。接下来4行表示玩具的目标状态,每行4个数字1或0,意义同上。
Output
一个整数,所需要的最少移动次数。
Sample Input
1111
0000
1110
0010
1010
0101
1010
0101
0000
1110
0010
1010
0101
1010
0101
Sample Output
4
可以发现用二进制表示状态的话最多也不会超过10^5,
所以我就直接想到bfs了,状态数<=10^5,转移代价算了算最多也就16*2=32。
虽然我觉得随便一个启发式搜索或者双向BFS都能打爆我一点优化没有的bfs,
但至少这个题BFS就够了,,,也懒的加优化了,,,(所以标签放的暴力)
/************************************************************** Problem: 1054 User: JYYHH Language: C++ Result: Accepted Time:20 ms Memory:1684 kb ****************************************************************/ #include<bits/stdc++.h> #define maxn 100005 using namespace std; int ans[maxn],S,T; int ci[30]; char ch; queue<int> q; inline void bfs(){ ans[S]=1,q.push(S); int x,to,a,b,c; while(!q.empty()){ x=q.front(),q.pop(); if(x==T){ printf("%d\n",ans[T]-1); return; } for(int i=0;i<16;i++){ a=(x&ci[i])?1:0,b=(x&ci[i+1])?1:0,c=(x&ci[i+4])?1:0; if((i&3)!=3&&(a^b)){ to=x^ci[i]^ci[i+1]; if(!ans[to]) ans[to]=ans[x]+1,q.push(to); } if(i<12&&(a^c)){ to=x^ci[i]^ci[i+4]; if(!ans[to]) ans[to]=ans[x]+1,q.push(to); } } } } int main(){ ci[0]=1; for(int i=1;i<=20;i++) ci[i]=ci[i-1]<<1; for(int i=1;i<=16;i++){ ch=getchar(); while(ch!='0'&&ch!='1') ch=getchar(); S=(S<<1)+ch-'0'; } for(int i=1;i<=16;i++){ ch=getchar(); while(ch!='0'&&ch!='1') ch=getchar(); T=(T<<1)+ch-'0'; } bfs(); return 0; }
我爱学习,学习使我快乐