1. 程式人生 > >洛谷 - P2730 - 魔板 Magic Squares - bfs

洛谷 - P2730 - 魔板 Magic Squares - bfs

!= == data r+ define urn bre ecan ack

寫狀態轉移弄了很久,老了,不記得自己的數組是怎麽標號的了。

#include <bits/stdc++.h>
using namespace std;
#define ll long long

static const int fac[] = {1, 1, 2, 6, 24, 120, 720, 5040, 40320, 362880,3628800};   // 階乘

//康托展開
int cantor(int *a,int n)
{
    int code=0;
    for(int i=0;i<n;i++)
    {
        int x=0;int c=1
,m=1;//c記錄後面的階乘 for(int j=i+1;j<n;j++) { if(a[j]<a[i])x++; m*=c;c++; } code+=x*m; } //printf("cantor=%d\n",code); return code; } //逆康托展開 void decantor(int code,int *a,int n){ bool vis[11]={}; for(int i=0;i<n;i++){
int r = code / fac[n-i-1]; code %= fac[n-i-1]; int cnt = 0; int j; for(j=1;j<=n;j++){ if(vis[j]==0){ cnt++; if(cnt==r+1){ a[i]=j; vis[j]=1; break; } } } }
/*printf("decantor="); for(int i=0;i<n;i++){ printf(" %d",a[i]); } printf("\n");*/ } void showdecantor(int code,int n){ int a[8]; bool vis[11]={}; for(int i=0;i<n;i++){ int r = code / fac[n-i-1]; code %= fac[n-i-1]; int cnt = 0; int j; for(j=1;j<=n;j++){ if(vis[j]==0){ cnt++; if(cnt==r+1){ a[i]=j; vis[j]=1; break; } } } } //printf("decantor="); for(int i=0;i<n;i++){ printf(" %d",a[i]); if(i%4==3) printf("\n"); } printf("\n"); } int encode(int *a) { int res=0; for(int i=0;i<16; i++) { if(a[i]) res|=1; res<<=1; } return res>>1; } void decode(int code,int *a) { for(int i=15; i>=0; i--) { a[i]=code&1; code>>=1; } } struct dat { int cur; int pre; char cha; } d,dt,data[40340]; queue<dat> q; void show(dat d) { stack<int> s; s.push(d.cur); while(1) { if(d.pre==-1) break; s.push(d.pre); d=data[d.pre]; } printf("%d\n",s.size()-1); int cur=s.top(); string ans=""; while(!s.empty()) { int nex=s.top(); s.pop(); //printf("%c\n",data[cur].cha); if(data[cur].cha!=N){ if(ans.length()>=60){ cout<<ans<<endl; ans=""; } ans+=data[cur].cha; } //showdecantor(cur,8); cur=nex; } if(data[cur].cha!=N){ if(ans.length()>=60){ cout<<ans<<endl; ans=""; } ans+=data[cur].cha; } cout<<ans<<endl; } int s,t; inline bool found(int code) { return (code==t); } int A(int code){ int a[8]; decantor(code,a,8); swap(a[0],a[7]); swap(a[1],a[6]); swap(a[2],a[5]); swap(a[3],a[4]); return cantor(a,8); } int B(int code){ int a[8]; decantor(code,a,8); int t1=a[3]; int t2=a[4]; a[3]=a[2]; a[2]=a[1]; a[1]=a[0]; a[0]=t1; a[4]=a[5]; a[5]=a[6]; a[6]=a[7]; a[7]=t2; return cantor(a,8); } int C(int code){ int a[8]; decantor(code,a,8); int t=a[1]; a[1]=a[6]; a[6]=a[5]; a[5]=a[2]; a[2]=t; return cantor(a,8); } void bfs() { memset(data,-1,sizeof(data)); d.cur=s; d.pre=-1; d.cha=N; data[d.cur]=d; if(found(d.cur)) { printf("0\n\n"); return; } q.push(d); while(!q.empty()) { d=q.front(); q.pop(); dt.cur=A(d.cur); if(data[dt.cur].cur==-1){ dt.pre=d.cur; dt.cha=A; data[dt.cur]=dt; if(found(dt.cur)){ show(dt); return; } q.push(dt); } dt.cur=B(d.cur); if(data[dt.cur].cur==-1){ dt.pre=d.cur; dt.cha=B; data[dt.cur]=dt; if(found(dt.cur)){ show(dt); return; } q.push(dt); } dt.cur=C(d.cur); if(data[dt.cur].cur==-1){ dt.pre=d.cur; dt.cha=C; data[dt.cur]=dt; if(found(dt.cur)){ show(dt); return; } q.push(dt); } } cout<<"NOFOUND"<<endl; } int main() { int a[8]; for(int i=0; i<8; i++) a[i]=i+1; s=cantor(a,8); for(int i=0; i<8; i++) scanf("%d",&a[i]); t=cantor(a,8); //decantor(t,a,8); bfs(); }

洛谷 - P2730 - 魔板 Magic Squares - bfs