AOJ2249 最短路+最小花费(双权值)
Posted codeoosacm
tags:
篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了AOJ2249 最短路+最小花费(双权值)相关的知识,希望对你有一定的参考价值。
写题解之前先骂一下这道题
xxx给数据范围点数<1e4,边数<2e4,结果我开2e4和3e4都RE,然后找问题一个多小时,最后我开了1e5和2e5,题面太能唬人了吧!?真是sb题面
------------------------------------------分割线------------------------------------
题目大意:给n个点和m条边,每条边给了起始点,距离和价格,求在保证点1到其他n-1个点的路径都是最短路的前提下所有路的价格之和的最小值
简单的Dijkstra变形,在松弛的时候做一下改变即可
1 #include<iostream> 2 #include<cstdio> 3 #include<queue> 4 #include<cstring> 5 #define mem(a,b) memset(a,b,sizeof(a)) 6 using namespace std; 7 struct edge 8 { 9 int to,nex,v,p; 10 }e[220000]; 11 int cnt,dis[110000],pri[110000]; 12 int vis[110000],fir[110000]; 13 struct node 14 { 15 int dis,pos; 16 node(){}; 17 node(int a,int b):dis(a),pos(b){} 18 bool operator<(const node &x)const 19 { 20 return dis>x.dis; 21 } 22 }; 23 void add_e(int fro,int to,int v,int p) 24 { 25 e[++cnt].v=v; 26 e[cnt].to=to; 27 e[cnt].nex=fir[fro]; 28 e[cnt].p=p; 29 fir[fro]=cnt; 30 } 31 void dij(int s) 32 { 33 priority_queue<node>q; 34 q.push(node(0,1)); 35 while(!q.empty()) 36 { 37 int now=q.top().pos; 38 q.pop(); 39 if(vis[now]) continue; 40 vis[now]=1; 41 for(int i=fir[now];i;i=e[i].nex) 42 { 43 int to=e[i].to; 44 if(dis[to]>dis[now]+e[i].v&&vis[to]==0) 45 { 46 dis[to]=dis[now]+e[i].v; 47 pri[to]=e[i].p; /*松弛以后更改花费,因为是由上一个点扩展来的,为了避免重复计数, 48 花费直接就是边的价格, 49 不理解的话可以这样想,所有的点都是由上一个点找到的, 50 然后最终会到第一个点,所以总的花费=这个点的花费+之前点的花费,一直推直到点1*/ 51 q.push(node(dis[to],to)); 52 } 53 else if(dis[to]==dis[now]+e[i].v)//注意此处一定要用else if,因为上一个if进行之后,这个if必定满足(或者把这个if写在前面) 54 { 55 pri[to]=min(e[i].p,pri[to]);//距离相同选择最小花费 56 } 57 } 58 } 59 } 60 void ini() 61 { 62 cnt=0; 63 fill(dis,dis+110000,99999999); 64 fill(pri,pri+110000,99999999); 65 mem(fir,0); 66 mem(e,0); 67 mem(vis,0); 68 } 69 int main() 70 { 71 int m,n; 72 while(scanf("%d%d",&n,&m)&&m+n) 73 { 74 ini(); 75 dis[1]=0; 76 for(int i=1;i<=m;i++) 77 { 78 int a,b,c,d; 79 cin>>a>>b>>c>>d; 80 add_e(a,b,c,d); 81 add_e(b,a,c,d); 82 } 83 dij(1); 84 int ans=0; 85 for(int i=2;i<=n;i++) 86 { 87 ans+=pri[i];//加起来就是总的花费 88 } 89 printf("%d ",ans); 90 } 91 return 0; 92 }
以上是关于AOJ2249 最短路+最小花费(双权值)的主要内容,如果未能解决你的问题,请参考以下文章
HDU - 3790最短路径问题(DIjkstra算法 双权值)
AOJ-2249-Road Construction-dijkstra-最小花费
AOJ 2249 Road Construction (dijkstra)