TYVJ 1541 八数码
Orz双向搜索的cy大神
我用的是hash 也蛮快的
//By SiriusRen
#include <queue>
#include <cstdio>
using namespace std;
#define mod 1000007
struct node{char a[4][4],cnt;}a,b;
char xx[]={1,-1,0,0},yy[]={0,0,1,-1};
int vis[1000007],jy,f;
queue<node>q;
bool check(int x,int y){
int temp=0;
if(x>=1&&x<=3&&y>=1&&y<=3){
for(int i=1;i<=3;i++){
for(int j=1;j<=3;j++){
temp=temp*10+a.a[i][j];
}
}
temp%=mod;
if(temp==jy){f=1;return 1;}
if(!vis[temp]){vis[temp]=1;return 1;}
return 0;
}
return 0;
}
int main(){
scanf("%c%c%c%c%c%c%c%c%c",&a.a[1][1],&a.a[1][2],&a.a[1][3],&a.a[2][1],&a.a[2][2],&a.a[2][3],&a.a[3][1],&a.a[3][2],&a.a[3][3]);
for(int i=1;i<=3;i++)for(int j=1;j<=3;j++)a.a[i][j]-='0';
b.a[1][1]=1,b.a[1][2]=2,b.a[1][3]=3,b.a[2][1]=8,b.a[2][3]=4,b.a[3][1]=7,b.a[3][2]=6,b.a[3][3]=5;
for(int i=1;i<=3;i++){
for(int j=1;j<=3;j++){
jy=jy*10+b.a[i][j];
}
}
jy%=mod;
q.push(a);
while(!q.empty()){
// for(int i=1;i<=3;i++)for(int j=1;j<=3;j++)printf("%d",a.a[i][j]);puts("");
a=q.front();q.pop();\
for(int i=1;i<=3;i++){
for(int j=1;j<=3;j++){
if(a.a[i][j]==0){
a.cnt++;
for(int k=0;k<=3;k++){
swap(a.a[i+xx[k]][j+yy[k]],a.a[i][j]);
if(check(i+xx[k],j+yy[k])){
if(f){printf("%d ",a.cnt);goto end;}
q.push(a);
}
swap(a.a[i+xx[k]][j+yy[k]],a.a[i][j]);
}
}
}
}
}
end:;
}