uvaoj 101 - The Blocks Problem(vector應用+技巧)
阿新 • • 發佈:2018-11-14
木塊問題,模擬堆的操作。每個堆的高度不確定,用vector來做很合適(vector動態)。
本題模擬四個操作:
1.move a onto b:把a和b上方的木塊全部放回原來的堆,然後把a摞在b上面
2.move a over b:把a上方的木塊全部放回原來的堆,然後把a放在b所在木塊堆的頂部
3.pile a onto b:把b上方的木塊全部放回原來的堆,然後把a及上面的木塊整體摞在b上面。
4.pile a over b:把a及上面的木塊整體摞在b所在木塊堆的頂部。
這裡有一個技巧:四種指令完全獨立處理會使程式碼變得複雜,容易出錯。所以可以提取出他們之間的共同點,以減少重複程式碼。
1 #include<bits/stdc++.h> 2 using namespace std; 3 const int maxn=30; 4 int n; 5 vector<int> pile[maxn];//每個pile[i]是一個vector 6 //找木塊a所在的pile和height,以引用的形式返回呼叫者 7 void find_block(inta,int& p,int& h) 8 { 9 for(p=0;p<n;p++) 10 { 11 for(h=0;h<pile[p].size();h++) 12 { 13 if(pile[p][h]==a)return; 14 } 15 } 16 } 17 //第P堆高度為h的木塊上方的所有木塊移回原位 18 void clear_above(int p,int h) 19 { 20 for(int i=h+1;i<pile[p].size();i++)21 { 22 int b=pile[p][i]; 23 pile[b].push_back(b); 24 } 25 pile[p].resize(h+1);//第p堆只保留下標在0~h之間的元素 26 } 27 //把第p堆高度為h及其上方的木塊整體移動到p2堆 28 void pile_onto(int p,int h,int p2) 29 { 30 for(int i=h;i<pile[p].size();i++) 31 { 32 pile[p2].push_back(pile[p][i]); 33 } 34 pile[p].resize(h);//第p堆只保留下標在0~h-1之間的元素 35 } 36 //列印函式 37 void print() 38 { 39 for(int i=0;i<n;i++) 40 { 41 printf("%d:",i); 42 for(int j=0;j<pile[i].size();j++)printf(" %d",pile[i][j]); 43 printf("\n"); 44 } 45 } 46 int main() 47 { 48 int a,b; 49 cin>>n; 50 string s1,s2; 51 for(int i=0;i<n;i++)pile[i].push_back(i);//初始化,給木塊賦上相應對的編號 52 while(cin>>s1) 53 { 54 if(s1!="quit")cin>>a>>s2>>b; 55 else break; 56 int pa,pb,ha,hb; 57 find_block(a,pa,ha); 58 find_block(b,pb,hb); 59 if(pa==pb)continue; 60 if(s2=="onto")clear_above(pb,hb); 61 if(s1=="move")clear_above(pa,ha); 62 pile_onto(pa,ha,pb); 63 } 64 print(); 65 return 0; 66 }