P1828 香甜的黄油 (spfa)

【题目描述】

    农夫John知道每只奶牛都在各自喜欢的牧场(一个牧场不一定只有一头牛)。给出各头牛在的牧场和牧场间的路线,找出使所有牛到达的路程和最短的牧场(他将把糖放在那)。

【题目链接】

    https://www.luogu.org/problemnew/show/P1828

【算法】

    算出任意两个牧场间最短距离,枚举目的地,取最小值。floyd会超时,对每个点用spfa。

【代码】

 1 #include <bits/stdc++.h>
 2 using namespace std;
 3 struct edge{ int to,next,val; }e[3010];
 4 int n,p,C,a,b,c,tot,ans=1e9,i,j;
 5 int head[810],rec[810],d[810][810],v[810];
 6 void add(int from,int to,int val)
 7 {
 8     e[++tot].to=to,e[tot].val=val;
 9     e[tot].next=head[from],head[from]=tot;
10 }
11 int main()
12 {
13     scanf("%d%d%d",&n,&p,&C);
14     for(i=1;i<=n;i++) scanf("%d",&a),rec[a]++;
15     for(i=1;i<=C;i++) scanf("%d%d%d",&a,&b,&c),add(a,b,c),add(b,a,c);
16     memset(d,0x3f,sizeof(d));
17     for(i=1;i<=p;i++) {
18         memset(v,0,sizeof(v));
19         queue<int> q;
20         d[i][i]=0;
21         q.push(i); v[i]=1;
22         while(q.size()) {
23             int x=q.front(); q.pop();
24             v[x]=0;
25             for(j=head[x];j;j=e[j].next) {
26                 int to=e[j].to,val=e[j].val;
27                 if(d[i][to]>d[i][x]+val) {
28                     d[i][to]=d[i][x]+val;
29                     if(!v[to]) q.push(to),v[to]=1;
30                 }
31             }
32         }
33     }
34     for(i=1;i<=p;i++) {
35         int tmp=0;
36         for(j=1;j<=p;j++)
37             tmp=tmp+d[i][j]*rec[j];
38         ans=min(ans,tmp);
39     }
40     printf("%d\n",ans);
41     return 0;
42 }

猜你喜欢

转载自www.cnblogs.com/Willendless/p/9436206.html
今日推荐