题意我就不说了,反向dijkstra,难点就是反向推物品数和字典序输出答案
这里我简单分析下,原来是20,通过一个城镇就变成了19,可以将一个数看成很多20,那么反推就是看多少19;
关于字典序,因为A字典序小于a,所以按照从小到大根据dis的值反推即可
1 //sevenkplus bless me 2 #include<iostream> 3 #include<cstdio> 4 #include<algorithm> 5 #include<stdlib.h> 6 #include<cctype> 7 #include<cmath> 8 #include<limits.h> 9 #include<iomanip> 10 #include<cstring> 11 #include<fstream> 12 #include<string> 13 #include<queue> 14 #include<stack> 15 #include<set> 16 #include<map> 17 #include<vector> 18 using namespace std; 19 const double pi = 4.0 * atan(1.0); 20 typedef signed long long LL; 21 #define clr(x) memset(x,0,sizeof(x)) 22 #define clro(x) memset(x,-1,sizeof(x)) 23 typedef pair<int,int> pii; 24 const int inf = 99999999; 25 const LL INF = 0x3f3f3f3f3f3f3f3fLL - 11111; 26 #define sf scanf 27 #define pf printf 28 const int maxn = 100; 29 int T = 0; 30 struct Dijkstra{ 31 LL dis[maxn] ; 32 bool w[maxn][maxn], vis[maxn],city[maxn]; 33 void clear(){ clr(w); clr(city); }; 34 LL cost( int x, int y){ 35 if( city[y] ){ 36 LL re = dis[x]/20; 37 if( dis[x]%20 != 0 ) ++re; 38 return re; 39 } 40 else return 1; 41 }; 42 LL recost( int x, int y){ 43 if( city[x] ){ 44 int re = dis[x]/19; 45 if( dis[x]%19 != 0 ) ++re; 46 return re; 47 } 48 else return 1; 49 }; 50 void path( int x, int t){ 51 if( x == t ){ 52 pf("%c\n",x + 'A' ); 53 return; 54 } 55 for( int y=0; y<maxn; ++y){ 56 if( w[x][y] && dis[x] - cost(x,y) == dis[y] ){ 57 pf("%c-",x+'A'); 58 path(y,t); 59 break; 60 } 61 }; 62 }; 63 LL dijkstra( int s, int t, LL star){ 64 int x,y; 65 LL m; 66 for( int i=0; i<maxn; ++i) dis[i] = INF; 67 clr(vis); dis[s] = star; 68 while(1){ 69 m = INF; x = -1; 70 for( y=0; y<maxn; ++y) 71 if( !vis[y] && dis[y] < m ) 72 m = dis[x = y]; 73 if( x == -1 ) break; 74 vis[x] = true; 75 for( y = 0; y<maxn; ++y) if( w[x][y] == 1 ) 76 dis[y] = min( dis[y] , dis[x] + recost(x,y) ); 77 }; 78 return dis[t]; 79 }; 80 }sol; 81 void solve( int n ){ 82 int a,b; 83 LL star; 84 char s[2]; 85 for( int i=0; i<n; ++i){ 86 sf("%s",s); a = s[0] - 'A'; 87 if( a < 26 ) sol.city[a] = true; 88 sf("%s",s); b = s[0] - 'A'; 89 if( b < 26 ) sol.city[b] = true; 90 sol.w[b][a] = sol.w[a][b] = 1; 91 } 92 sf("%lld", &star); 93 sf("%s",s); a = s[0] - 'A'; 94 if( a < 26 ) sol.city[a] = true; 95 sf("%s",s); b = s[0] - 'A'; 96 if( b < 26 ) sol.city[b] = true; 97 pf("Case %d:\n",++T); 98 pf("%lld\n",sol.dijkstra(b,a,star) ); 99 sol.path(a,b); 100 }; 101 int main(){ 102 int n; 103 while( sf("%d",&n) == 1 ){ 104 if( n == -1 ) break; 105 sol.clear(); 106 solve(n); 107 } 108 return 0; 109 }