标签:
vijosP1285 佳佳的魔法药水
【思路】
图论思想。
很巧妙。
如A+B=C,将AB之间连边,边权为C,用以找相连物品与合成物。
用Dijkstra的思想:找最小价值,如果相连物品中有已经得出最小价值的则共同更新其合成物。
对于方案数用乘法原理在更新的时候顺便计算。
【代码】
1 #include<iostream> 2 #include<cstring> 3 #include<cstdio> 4 using namespace std; 5 6 const int maxn = 1000+10; 7 const int INF=1<<30; 8 9 int G[maxn][maxn],d[maxn],vis[maxn]; 10 int tot[maxn]; 11 int n; 12 13 int main(){ 14 ios::sync_with_stdio(false); 15 cin>>n; 16 for(int i=0;i<n;i++) cin>>d[i]; 17 18 for(int i=0;i<n;i++) 19 { 20 tot[i]=1; 21 for(int j=0;j<n;j++) G[i][j]=-1; 22 } 23 24 int u,v,w; 25 while(cin>>u>>v>>w) { 26 G[u][v]=G[v][u]=w; 27 } 28 for(int i=0;i<n;i++) { 29 int _min=INF,k; 30 for(int j=0;j<n;j++) if(!vis[j] && d[j]<_min) _min=d[k=j]; 31 if(_min==INF) break; 32 vis[k]=1; 33 for(int j=0;j<n;j++) if(vis[j] && G[k][j]>=0) //注意是vis[j]//寻找已经得到最小价值的更新其合成物 34 if(d[G[k][j]]>d[k]+d[j]) { 35 d[G[k][j]]=d[k]+d[j]; 36 tot[G[k][j]]=tot[k]*tot[j]; 37 } 38 else 39 if(d[G[k][j]]==d[k]+d[j]) 40 tot[G[k][j]] += tot[k]*tot[j]; 41 } 42 cout<<d[0]<<" "<<tot[0]<<"\n"; 43 return 0; 44 }
标签:
原文地址:http://www.cnblogs.com/lidaxin/p/4905162.html