HDU1535 Invitation Cards 堆优化

题意:从起点1到另外所有点的距离之和加上,另外所有点到1的距离之和,来去的花费不同。

两次Dijkstra,第二次反方向时,改变始末位置便可套用之前的Dijkstra模板。

 1 #include<cstdio>
 2 #include<queue>
 3 #include<algorithm>
 4 #include<vector>
 5 #define maxn 1000010
 6 using namespace std;
 7 int n, m,ans = 0;
 8 int a[maxn], b[maxn], c[maxn], dis[maxn];
 9 bool done[maxn];
10 const int inf=0x3f3f3f3f;
11 struct edge {
12     int from, to, w;
13 };
14 vector<edge>e[maxn];
15 struct s_node {
16     int id, n_dis;
17     bool operator<(const s_node& a)const { return n_dis > a.n_dis; }
18 };
19 void init() {for (int i = 1;i <= m;i++)dis[i] = inf, done[i] = false;}
20 void INIT() {for (int i = 1;i <= m;i++)e[i].clear();}
21 void dij() {
22     int s = 1;
23     init();
24     dis[s] = 0;
25     priority_queue<s_node>Q;
26     Q.push( s_node{s,dis[s]} );
27     while (!Q.empty()) {
28         s_node u = Q.top();
29         Q.pop();
30         if (done[u.id])continue;
31         done[u.id] = true;
32         int len = e[u.id].size();
33         for (int i = 0;i < len;i++) {
34             edge y = e[u.id][i];
35             if (done[y.to])continue;
36             if (dis[y.to] > y.w + u.n_dis) {
37                 dis[y.to] = y.w + u.n_dis;
38                 Q.push({ y.to,dis[y.to] });
39             }
40         }
41     }
42     INIT();
43     for (int i = 2;i <= n;i++)ans += dis[i];
44 }
45 int main()
46 {
47     int T;
48     scanf("%d", &T);
49     while (T--) {        
50         ans = 0;
51         scanf("%d%d", &n, &m);    
52         for(int i=1;i<=m;i++)scanf("%d%d%d", &a[i], &b[i], &c[i]);
53         for(int i=1;i<=m;i++)e[a[i]].push_back(edge{ a[i],b[i],c[i] });
54         dij();
55         for (int i = 1;i <= m;i++)e[b[i]].push_back(edge{ b[i],a[i],c[i] });
56         dij();
57         printf("%d\n", ans);    
58     }
59 }

 

posted @ 2020-02-29 22:39  programmer_w  阅读(136)  评论(0编辑  收藏  举报