1. 程式人生 > >2016 ACM/ICPC 區域賽(北京) E 題 bfs

2016 ACM/ICPC 區域賽(北京) E 題 bfs

解析 一個 區域賽 pac () get 標記 數組 swap

https://vjudge.net/problem/UVALive-7672

題意 輸入一個五位數n 問由12345變到n的操作最少次數 不可達輸出-1

有三種操作

1.交換相鄰的位置 次數不限制

2.使某一位上的數字+1 最多使用三次 (mod 10)

3.使某一位上的數字*2 最多使用兩次 (mod 10)

解析 很容易想到預處理,然後O(1) 查詢,操作次數最少,所以就bfs,一層一層向外拓展。

需要註意的是 一個數被訪問過還可以再被訪問(進隊列),因為得到一個數可以有不同的操作方案,我們都需要將它向下進行擴展

比如說 26345

可 以 12345->22345(1+1)->23345->26345 (兩次2操作,一次3操作)

還可以 12345->22345(1 * 2)->23345->26345 (一次2操作,兩次3操作)

兩個狀態都要進隊列才能滿足答案正確性。然後開個三維數組記錄vis[26345][2][1]標記這個狀態訪問過了。

 1 #include<bits/stdc++.h>
 2 using namespace std;
 3 const int inf=0x3f3f3f3f;
 4 int ans[100000][1];
 5 int vis[100000][4][3]; //0 swap,1 +,2 double
 6 struct node
 7 {
 8     string s;
9 int a,b,c; 10 }; 11 int change(string s)//string 轉int 12 { 13 int x=1,ans=0; 14 for(int i=s.length()-1;i>=0;i--) 15 { 16 ans+=(int)(s[i]-0)*x; 17 x*=10; 18 } 19 return ans; 20 } 21 void bfs() 22 { 23 memset(ans,inf,sizeof(ans)); 24 memset(vis,0,sizeof(vis));
25 queue<node>q; 26 string beg="12345"; 27 q.push({beg,0,0,0}); 28 ans[change(beg)][0]=0; 29 while(!q.empty()) 30 { 31 node e=q.front(); 32 string now=e.s;q.pop(); 33 int noww=change(now); 34 if(e.b<3) 35 { 36 for(int i=0;i<5;i++) 37 { 38 string t=now; 39 if(t[i]==9) t[i]=0; 40 else t[i]++; 41 int temp=change(t); 42 if(!vis[temp][e.b+1][e.c]) 43 { 44 vis[temp][e.b+1][e.c]=1; 45 ans[temp][0]=min(ans[temp][0],e.a+e.b+e.c+1); 46 q.push({t,e.a,e.b+1,e.c}); 47 } 48 } 49 } 50 if(e.c<2) 51 { 52 for(int i=0;i<5;i++) 53 { 54 string t=now; 55 int k=t[i]-0; 56 k+=k,k%=10; 57 t[i]=0+k; 58 int temp=change(t); 59 if(!vis[temp][e.b][e.c+1]) 60 { 61 vis[temp][e.b][e.c+1]=1; 62 ans[temp][0]=min(ans[temp][0],e.a+e.b+e.c+1); 63 q.push({t,e.a,e.b,e.c+1}); 64 } 65 } 66 } 67 for(int i=0;i<4;i++) 68 { 69 string t=now; 70 swap(t[i],t[i+1]); 71 int temp=change(t); 72 if(ans[temp][0]==inf) 73 { 74 ans[temp][0]=min(ans[temp][0],e.a+e.b+e.c+1); 75 q.push({t,e.a+1,e.b,e.c}); 76 } 77 } 78 } 79 } 80 int main() 81 { 82 bfs(); 83 string s; 84 while(cin>>s) 85 { 86 int x=change(s); 87 if(ans[x][0]==inf) 88 cout<<-1<<endl; 89 else 90 cout<<ans[x][0]<<endl; 91 } 92 }

2016 ACM/ICPC 區域賽(北京) E 題 bfs