1. 程式人生 > >P1242 【新漢諾塔】

P1242 【新漢諾塔】

設有n個大小不等的中空圓盤,按從小到大的順序從1到n編號。將這n個圓盤任意的迭套在三根立柱上,立柱的編號分別為A、B、C,這個狀態稱為初始狀態。

現在要求找到一種步數最少的移動方案,使得從初始狀態轉變為目標狀態。

移動時有如下要求:

·一次只能移一個盤;

·不允許把大盤移到小盤上面。

從洛谷上找來的題解,沒有時間做,但還是覺得這題挺好

 1 #include<cstdio>
 2 int n,last[55],first[55],ans=0,m,x;
 3 const char ch[]={'0','A','B','C'};
 4 //char陣列的第一位要有零佔位,調了n久呀,一定要吸取教訓。
5 void dfs(int x,int y) 6 { 7 if(first[x]==y) return; 8 for(int i=x-1;i>=1;i--) dfs(i,6-(first[x]+y)); 9 //處理小盤子。 10 printf("move %d from %c to %c\n",x,ch[first[x]],ch[y]); 11 //輸出。 12 first[x]=y;ans++; 13 //類似於並查集,找完就將x,y合併,並且累加答案數。 14 } 15 int main() 16 { 17 scanf("
%d",&n); 18 for(int i=1;i<=3;i++) 19 { 20 scanf("%d",&m); 21 for(int j=1;j<=m;j++) scanf("%d",&x),first[x]=i; 22 } 23 for(int i=1;i<=3;i++) 24 { 25 scanf("%d",&m); 26 for(int j=1;j<=m;j++) scanf("%d",&x),last[x]=i; 27
} 28 //將每一個目標與初始柱打上標記 29 for(int i=n;i>=1;i--) dfs(i,last[i]); 30 //第i個要到目標柱那裡去。 31 printf("%d",ans); 32 return 0; 33 }