【模板·次短路】 洛谷 P2865 [USACO06NOV]路障Roadblocks
阿新 • • 發佈:2018-12-19
思路:
次短路模板。
正反求最短路dist1[x]和dist2[x],表示1到x的最短路和x到1的最短路。
列舉每條邊更新答案。
注意:priority_queue是大根堆!<運算子不能定義錯!
程式碼:
#include<bits/stdc++.h>
using namespace std;
#define maxn 5000
#define maxm 100000
#define read(x) scanf("%d",&x)
struct Edge{
int x,y,z;
Edge(){}
Edge(int xx,int yy,int zz) {
x=xx,y=yy, z=zz;
}
};
struct Pair{
int y,z;
Pair(){}
Pair(int yy,int zz) {
y=yy,z=zz;
}
bool operator < (const Pair& oth) const {
return z>oth.z;
}
};
int n,m;
vector<Edge> g[maxn+5];
int dist1[maxn+5],dist2[maxn+5];
priority_queue<Pair> que;
bool vis[maxn+5];
Edge e[maxm+5 ];
void dijkstra(int s,int t,int* dist) {
priority_queue<Pair> emp;
que=emp;
for(int i=1;i<=n;i++) if(i!=s) dist[i]=1e9;
que.push(Pair(s,0));
memset(vis,0,sizeof(vis));
while(!que.empty()) {
int h=que.top().y;
que.pop();
if(vis[h]) continue;
vis[h]=true;
for(int i=0;i<g[ h].size();i++) {
int x=g[h][i].y,z=g[h][i].z;
if(dist[x]>dist[h]+z) {
dist[x]=dist[h]+z;
que.push(Pair(x,dist[x]));
}
}
}
}
int main() {
read(n),read(m);
for(int i=1;i<=m;i++) {
int x,y,z;
read(x),read(y),read(z);
g[x].push_back(Edge(x,y,z));
g[y].push_back(Edge(y,x,z));
e[i]=Edge(x,y,z);
}
dijkstra(1,n,dist1);
dijkstra(n,1,dist2);
int d=dist1[n],ans=1e9;
for(int i=1;i<=m;i++) {
int d1=dist1[e[i].x]+dist2[e[i].y]+e[i].z;
int d2=dist2[e[i].x]+dist1[e[i].y]+e[i].z;
if(d1<ans&&d1!=d) ans=d1;
if(d2<ans&&d2!=d) ans=d2;
}
printf("%d",ans);
return 0;
}