2 2 2 1 2 13 2 1 33 4 6 1 2 10 2 1 60 1 3 20 3 4 10 2 4 5 4 1 50
46 210
题目分析:这题HDU的数据比较水,给的时间也短,POJ的数据超int,wa了几发,做法就是1到各点直接spfa搞一下,反过来,就把图也反过来建一下,再搞一次spfa就可以了,一套好板子也是很重要的,书上板子动态分配伤不起,其实vector也挺费时,在poj跑了4000ms+,但是比较好写
POJ:
#include <cstdio> #include <cstring> #include <vector> #include <queue> #define ll long long int const MAX = 1e6 + 5; ll const INF = 0xffffffff; using namespace std; struct NODE { int v, w; NODE(int vv, ll ww) { v = vv; w = ww; } }; struct EDGE { int u, v; ll w; }e[MAX]; vector <NODE> vt[MAX]; int p, q; ll ans, dist[MAX]; bool vis[MAX]; void SPFA(int v0) { memset(vis, false, sizeof(vis)); for(int i = 0; i <= p; i++) dist[i] = INF; dist[v0] = 0; queue <int> Q; Q.push(v0); while(!Q.empty()) { int u = Q.front(); Q.pop(); vis[u] = false; int sz = vt[u].size(); for(int i = 0; i < sz; i++) { int v = vt[u][i].v; ll w = vt[u][i].w; if(dist[v] > dist[u] + w) { dist[v] = dist[u] + w; if(!vis[v]) { Q.push(v); vis[v] = true; } } } } } void Clear() { for(int i = 1; i <= p; i++) vt[i].clear(); } int main() { int T; scanf("%d", &T); while(T--) { ans = 0; scanf("%d %d", &p, &q); for(int i = 0; i < q; i++) scanf("%d %d %lld", &e[i].u, &e[i].v, &e[i].w); Clear(); for(int i = 0; i < q; i++) vt[e[i].u].push_back(NODE(e[i].v, e[i].w)); SPFA(1); for(int i = 1; i <= p; i++) ans += dist[i]; Clear(); for(int i = 0; i < q; i++) vt[e[i].v].push_back(NODE(e[i].u, e[i].w)); SPFA(1); for(int i = 1; i <= p; i++) ans += dist[i]; printf("%lld\n", ans); } }
HDU:
#include <cstdio> #include <cstring> #include <vector> #include <queue> int const MAX = 1e6 + 5; int const INF = 0xfffffff; using namespace std; struct NODE { int v, w; NODE(int vv, int ww) { v = vv; w = ww; } }; struct EDGE { int u, v, w; }e[MAX]; vector <NODE> vt[MAX]; int p, q, ans, dist[MAX]; bool vis[MAX]; void SPFA(int v0) { memset(vis, false, sizeof(vis)); for(int i = 0; i <= p; i++) dist[i] = INF; dist[v0] = 0; queue <int> Q; Q.push(v0); while(!Q.empty()) { int u = Q.front(); Q.pop(); vis[u] = false; int sz = vt[u].size(); for(int i = 0; i < sz; i++) { int v = vt[u][i].v; int w = vt[u][i].w; if(dist[v] > dist[u] + w) { dist[v] = dist[u] + w; if(!vis[v]) { Q.push(v); vis[v] = true; } } } } } void Clear() { for(int i = 1; i <= p; i++) vt[i].clear(); } int main() { int T; scanf("%d", &T); while(T--) { ans = 0; scanf("%d %d", &p, &q); for(int i = 0; i < q; i++) scanf("%d %d %d", &e[i].u, &e[i].v, &e[i].w); Clear(); for(int i = 0; i < q; i++) vt[e[i].u].push_back(NODE(e[i].v, e[i].w)); SPFA(1); for(int i = 1; i <= p; i++) ans += dist[i]; Clear(); for(int i = 0; i < q; i++) vt[e[i].v].push_back(NODE(e[i].u, e[i].w)); SPFA(1); for(int i = 1; i <= p; i++) ans += dist[i]; printf("%d\n", ans); } }
HDU 1535 && POJ 1511 Invitation Cards (SPFA 模板 + 反向建图)
原文地址:http://blog.csdn.net/tc_to_top/article/details/43676145