zoj 2526(一道很好的最短路应用题)

题目链接:http://acm.zju.edu.cn/onlinejudge/showProblem.do?problemId=1538

题意:最短路问题,但是要求出最短路的条数,同时要求出所有可能的最短路选择中javabean最多的情况。

思路:求到终点的最短路径用Dijkstra,其路径更新条件(如果到某个点有多个路径长度一样的最短路径,则选择豆子总数最多的)就是直接加个else if条件就搞定了,最后就是dfs搜一下最短路的条数了,这个我就记忆化了一下。

然后我一开始使用spfa写的,wa了好多次,orz...改成dijkstra就过了。

  1 #include<iostream>
  2 #include<cstdio>
  3 #include<cstring>
  4 #include<queue>
  5 #include<vector>
  6 using namespace std;
  7 #define MAXN 555
  8 #define inf 1<<30
  9 /*
 10 struct Node{
 11     int v,w;
 12 };
 13 vector<Node>vet[MAXN];
 14 */
 15 int map[MAXN][MAXN];
 16 int path[MAXN];
 17 int dist[MAXN];
 18 int value[MAXN];
 19 int sum_value[MAXN];
 20 int dp[MAXN];
 21 int mark[MAXN];
 22 int n,m,st,ed;
 23 
 24 /*
 25 void SPFA(){
 26     memset(sum_value,0,sizeof(sum_value));
 27     memset(path,-1,sizeof(path));
 28     for(int i=0;i<n;i++)dist[i]=inf;
 29     dist[st]=0,sum_value[st]=value[st];
 30     queue<int>Q;
 31     Q.push(st);
 32     while(!Q.empty()){
 33         int u=Q.front();
 34         Q.pop();
 35         for(int i=0;i<vet[u].size();i++){
 36             int v=vet[u][i].v;
 37             int w=vet[u][i].w;
 38             if(dist[u]+w<=dist[v]){
 39                 path[v]=u;
 40                 Q.push(v);
 41                 if(dist[u]+w<dist[v]){
 42                     dist[v]=dist[u]+w;
 43                     sum_value[v]=sum_value[u]+value[v];
 44                 }else if(sum_value[v]<sum_value[u]+value[v]){
 45                     sum_value[v]=sum_value[u]+value[v];
 46                 }
 47             }
 48         }
 49     }
 50 }
 51 */
 52 
 53 void Dijkstra(){
 54     memset(mark,false,sizeof(mark));
 55     memset(sum_value,0,sizeof(sum_value));
 56     memset(path,-1,sizeof(path));
 57     for(int i=0;i<n;i++)dist[i]=map[st][i];
 58     dist[st]=0,sum_value[st]=value[st],mark[st]=true;
 59     int u=st;
 60     for(int i=0;i<n-1;i++){
 61         int min=inf;
 62         for(int j=0;j<n;j++){
 63             if(!mark[j]&&map[u][j]<inf&&dist[u]+map[u][j]<=dist[j]){
 64                 if(dist[u]+map[u][j]<dist[j]){
 65                     dist[j]=dist[u]+map[u][j];
 66                     sum_value[j]=sum_value[u]+value[j];
 67                     path[j]=u;
 68                 }else if(sum_value[j]<sum_value[u]+value[j]){
 69                     sum_value[j]=sum_value[u]+value[j];
 70                     path[j]=u;
 71                 }
 72             }
 73         }
 74         for(int j=0;j<n;j++){
 75             if(!mark[j]&&min>dist[j]){
 76                 min=dist[j],u=j;
 77             }
 78         }
 79         mark[u]=true;
 80     }
 81 }
 82     
 83 
 84 
 85 /*
 86 int dfs(int u){
 87     if(u==ed)return 1;
 88     if(dp[u])return dp[u];
 89     for(int i=0;i<vet[u].size();i++){
 90         int v=vet[u][i].v;
 91         int w=vet[u][i].w;
 92         if(dist[v]==dist[u]+w){
 93             dp[u]+=dfs(v);
 94         }
 95     }
 96     return dp[u];
 97 }
 98 */
 99 
100 int dfs(int u){
101     if(u==ed)return 1;
102     if(dp[u])return dp[u];
103     for(int i=0;i<n;i++)if(u!=i){
104         if(dist[i]==dist[u]+map[u][i]){
105             dp[u]+=dfs(i);
106         }
107     }
108     return dp[u];
109 }
110 
111 
112 void Print(int u){
113     if(path[u]==-1){
114         printf("%d",u);
115         return ;
116     }
117     Print(path[u]);
118     printf(" %d",u);
119 }
120 
121 int main(){
122     int u,v,w;
123     while(~scanf("%d%d%d%d",&n,&m,&st,&ed)){
124     //    for(int i=0;i<n;i++)vet[i].clear();
125         for(int i=0;i<n;i++){
126             map[i][i]=0;
127             for(int j=i+1;j<n;j++){
128                 map[i][j]=map[j][i]=inf;
129             }
130         }
131         for(int i=0;i<n;i++)
132             scanf("%d",&value[i]);
133         for(int i=1;i<=m;i++){
134             scanf("%d%d%d",&u,&v,&w);
135             /*
136             Node p1,p2;
137             p1.v=v,p2.v=u;
138             p1.w=p2.w=w;
139             vet[u].push_back(p1);
140             vet[v].push_back(p2);
141             */
142             map[u][v]=map[v][u]=w;
143         }
144     //    SPFA();
145         Dijkstra();
146         memset(dp,0,sizeof(dp));
147         int ans=dfs(st);
148         printf("%d %d\n",ans,sum_value[ed]);
149         Print(ed);
150         puts("");
151     }
152     return 0;
153 }
View Code
原文地址:https://www.cnblogs.com/wally/p/3078757.html