标签:
题意:一个帝国有 n 个城市,可以在城市两两之间建立 m 条高速公路,建立 x-y 之间的高速路需要时间 d,花费为 c,
最后建立完边(<=m)后使得首都 0 号城市到各个城市(1~n-1)的总时间最少,在多个时间满足条件下再选花费最少的。
思路:直接spfa,当有多个点使得时间最少时,选花费最小的边。
#include <iostream> #include <algorithm> #include <string.h> #include <stdio.h> #include <vector> #include <queue> using namespace std; #define LL long long #define MAX 999999999999 #define maxn 100005 struct node { int to,nex; LL v,cost; } p[4*maxn]; int h[maxn],cnt,n,m; LL d[maxn],c[maxn]; bool inq[maxn]; void init() { for(int i=0; i<maxn; i++) inq[i]=0; for(int i=0; i<maxn; i++) d[i]=MAX; for(int i=0; i<maxn; i++) c[i]=MAX; for(int i=0; i<maxn; i++) h[i]=0; cnt=0; } void add(int u,int v,LL w,LL cc) { cnt++; p[cnt].v=w; p[cnt].cost=cc; p[cnt].to=v; p[cnt].nex=h[u]; h[u]=cnt; } void spfa() { queue<int>q; q.push(0); d[0]=0; inq[0]=1; while(!q.empty()) { int now=q.front(); q.pop(); inq[now]=0; for(int i=h[now]; i>0; i=p[i].nex) { if(d[p[i].to]>d[now]+p[i].v) { d[p[i].to]=d[now]+p[i].v; c[p[i].to]=p[i].cost; if(inq[p[i].to]==0) { inq[p[i].to]=1; q.push(p[i].to); } } else if(d[p[i].to]==d[now]+p[i].v) { if(c[p[i].to]>p[i].cost) { c[p[i].to]=p[i].cost; if(inq[p[i].to]==0) { inq[p[i].to]=1; q.push(p[i].to); } } } } } return; } int main() { int T; cin>>T; while(T--) { init(); cin>>n>>m; for(int i=0; i<m; i++) { int x,y; LL w,z; scanf("%d%d%lld%lld",&x,&y,&w,&z); add(x,y,w,z); add(y,x,w,z); } spfa(); LL ans1=0,ans2=0; for(int i=1;i<n;i++) ans1+=d[i],ans2+=c[i]; printf("%lld %lld\n",ans1,ans2); } return 0; }
标签:
原文地址:http://www.cnblogs.com/zuferj115/p/5429152.html