A - Age of Moyu
题意:给出一张图,从1走到n,如果相邻两次走的边的权值不同,花费+1, 否则花费相同,求最小花费
思路:用set记录有当前点的最小花费有多少种方案到达,然后最短路
1 #include<bits/stdc++.h> 2 3 using namespace std; 4 5 const int INF = 0x3f3f3f3f; 6 const int maxn = 2e5 + 10; 7 8 struct Edge{ 9 int to, nxt, val; 10 Edge(){} 11 Edge(int to, int nxt, int val):to(to), nxt(nxt), val(val){}; 12 }edge[maxn << 1]; 13 14 set<int>s[maxn]; 15 int head[maxn], tot; 16 17 void Init(int n) 18 { 19 for(int i = 0; i <= n; ++i) head[i] = -1, s[i].clear(); 20 tot = 0; 21 } 22 23 void addedge(int u, int v,int val) 24 { 25 edge[tot] = Edge(v, head[u], val);head[u] = tot++; 26 } 27 28 struct qnode{ 29 int v, c; 30 int pre; 31 int fa; 32 qnode(){} 33 qnode(int v, int c, int pre, int fa) :v(v), c(c), pre(pre), fa(fa){} 34 bool operator < (const qnode &r) const 35 { 36 return c > r.c; 37 } 38 }; 39 40 int n, m; 41 int dist[maxn]; 42 43 void BFS(int st) 44 { 45 for(int i = 1; i <= n; ++i) dist[i] = INF; 46 priority_queue<qnode>q; 47 dist[st] = 0; 48 q.push(qnode(st, 0, 0, 0)); 49 while(!q.empty()) 50 { 51 qnode tmp = q.top(); 52 q.pop(); 53 int u = tmp.v; 54 if(tmp.c > dist[u]) continue; 55 else if(tmp.c == dist[u]) 56 { 57 if(s[u].find(tmp.pre) != s[u].end()) continue; 58 s[u].insert(tmp.pre); 59 } 60 else 61 { 62 dist[u] = tmp.c; 63 s[u].clear(); 64 s[u].insert(tmp.pre); 65 } 66 for(int i = head[u]; ~i; i = edge[i].nxt) 67 { 68 int v = edge[i].to; 69 int cost = edge[i].val; 70 if(v == tmp.fa) continue; 71 if(dist[u] + (cost != tmp.pre) <= dist[v]) 72 { 73 dist[v] = dist[u] + (cost != tmp.pre); 74 if(v != n) 75 { 76 q.push(qnode(v, dist[v], cost, u)); 77 } 78 } 79 } 80 } 81 } 82 83 int main() 84 { 85 int t; 86 while(scanf("%d %d", &n, &m) != EOF) 87 { 88 Init(n); 89 for(int i = 1; i <= m; ++i) 90 { 91 int u, v, w; 92 scanf("%d %d %d", &u, &v ,&w); 93 addedge(u, v, w); 94 addedge(v, u, w); 95 } 96 BFS(1); 97 if(dist[n] == INF) dist[n] = -1; 98 printf("%d\n", dist[n]); 99 } 100 return 0; 101 }