UVA - 11882 Biggest Number(dfs+bfs+强剪枝)
题目大意:给出一个方格矩阵,矩阵中有数字0~9,任选一个格子为起点,将走过的数字连起来构成一个数,找出最大的那个数,每个格子只能走一次。
题目分析:DFS。剪枝方案:在当前的处境下,找出所有还能到达的点的个数,若当前数字的长度加上个数仍小于目前最优答案的长度,则剪去;若长度相等,则将所有还能到达的数字按从大到小排序后连到当前数字上,如果还比目前最优解小,则减去。找出所有还能到达的点的过程用BFS实现。
1 #pragma comment(linker, "/STACK:1024000000,1024000000") 2 #include<iostream> 3 #include<cstdio> 4 #include<cstring> 5 #include<cmath> 6 #include<math.h> 7 #include<algorithm> 8 #include<queue> 9 #include<set> 10 #include<bitset> 11 #include<map> 12 #include<vector> 13 #include<stdlib.h> 14 #include <stack> 15 using namespace std; 16 #define PI acos(-1.0) 17 #define max(a,b) (a) > (b) ? (a) : (b) 18 #define min(a,b) (a) < (b) ? (a) : (b) 19 #define ll long long 20 #define eps 1e-10 21 #define MOD 1000000007 22 #define N 16 23 #define M 36 24 #define inf 1e12 25 int n,m; 26 char mp[N][N]; 27 int vis[N][N]; 28 int flag[N][N]; 29 int can[N<<2]; 30 int dirx[]={0,0,-1,1}; 31 int diry[]={-1,1,0,0}; 32 string ans; 33 34 bool smaller(string a,string b){ 35 if(a.size()<b.size()) { 36 return true; 37 } 38 if(a.size()==b.size()){ 39 if(a<b){ 40 return true; 41 } 42 } 43 return false; 44 } 45 46 bool ok(int x,int y){ 47 if(x<0 || x>=n || y<0 || y>=m || mp[x][y]=='#') return false; 48 return true; 49 } 50 int bfs(int x,int y){ 51 queue<int> q; 52 q.push(x*M+y); 53 memset(flag,0,sizeof(flag)); 54 flag[x][y]=1; 55 int step=0; 56 while(!q.empty()){ 57 int t=q.front(); 58 q.pop(); 59 60 for(int i=0;i<4;i++){ 61 int tx=t/M; int ty=t%M; 62 tx+=dirx[i]; ty+=diry[i]; 63 if(vis[tx][ty] || flag[tx][ty] || !ok(tx,ty)) continue; 64 can[step++]=mp[tx][ty]-'0'; 65 flag[tx][ty]=1; 66 q.push(tx*M+ty); 67 } 68 } 69 return step; 70 } 71 72 void dfs(int x,int y,string tmp){ 73 if(smaller(ans,tmp)){ 74 ans=tmp; 75 } 76 int get_step=bfs(x,y); 77 if(get_step+tmp.size()<ans.size()){ 78 return; 79 } 80 if(get_step+tmp.size()==ans.size()){ 81 sort(can,can+get_step); 82 string now=tmp; 83 for(int i=get_step-1;i>=0;i--){ 84 now+=char(can[i]+'0'); 85 } 86 if(smaller(now,ans)){ 87 return; 88 } 89 } 90 for(int i=0;i<4;i++){ 91 int tx=x+dirx[i]; 92 int ty=y+diry[i]; 93 if(vis[tx][ty] || !ok(tx,ty)) continue; 94 95 vis[tx][ty]=1; 96 dfs(tx,ty,tmp+mp[tx][ty]); 97 vis[tx][ty]=0; 98 } 99 } 100 int main() 101 { 102 while(scanf("%d%d",&n,&m)==2){ 103 if(n==0 && m==0){ 104 break; 105 } 106 for(int i=0;i<n;i++){ 107 scanf("%s",mp[i]); 108 } 109 ans.clear(); 110 memset(vis,0,sizeof(vis)); 111 for(int i=0;i<n;i++){ 112 for(int j=0;j<m;j++){ 113 if(mp[i][j]!='#'){ 114 vis[i][j]=1; 115 string tmp; tmp.clear(); 116 tmp+=mp[i][j]; 117 dfs(i,j,tmp); 118 vis[i][j]=0; 119 } 120 } 121 } 122 cout<<ans<<endl; 123 124 } 125 return 0; 126 }