Description
在一个图上有许多个农场,有个人从1农场出发,到他的朋友n农场去,他不想走一条最短路径,这次他想换条路走,要你帮他找一条次短路径,次短路的定义是,比最短路径长度短(可能有多条),但是不会比其他的路径长度长。而且告诉你数据中一定存在至少一条次短路。
Input
第一行两个整数n和r分别表示农场个数和路径条数,之后r行每行三个整数a,b,d表示a农场与b农场之间有一条长度为d的路径
Output
输出次短路长度
Sample Input
4 4
1 2 100
2 4 200
2 3 250
3 4 100
Sample Output
450
Solution
利用最短路的思想,最短路是维护每个节点到起点的最短距离,每次确定未确定里面距离最短的那个节点的最短距离,根据次短路定义,从S到u的第二短的路线,那么只要维护一下次短路就可以了
Code
#include<iostream>
#include<stdio.h>
#include<vector>
#include<queue>
#include<memory.h>
#include<fstream>
using namespace std;
const int INF=1<<29;
const int nMax=10000;
struct edge{
edge(){}
edge(int x,int y)
{
cost=x;
to=y;
}
bool operator<(const edge& rhs)const
{
return cost>rhs.cost;
}
int cost;
int to;
};
vector<edge>node[nMax];
int dist1[nMax];//最短路
int dist2[nMax];//次短路
void dijkstra(int s)
{
for(int i=0;i<nMax;++i)//初始化
dist1[i]=INF;
for(int i=0;i<nMax;++i)//初始化
dist2[i]=INF;
dist1[s]=0;
priority_queue<edge,vector<edge> > q;
q.push(edge(0,s));
edge u;
while(!q.empty())
{
u=q.top();
q.pop();
int sz=node[u.to].size();
int v=u.to;
if(u.cost>dist2[v])
continue;
for(int i=0;i<sz;++i)
{
int next=node[v][i].to;
int d=node[v][i].cost+u.cost;
if(d<dist1[next])//维护最短路
{
swap(d,dist1[next]);
q.push(edge(dist1[next],next));
}
if(d>dist1[next]&&d<dist2[next])//维护次短路
{
dist2[next]=d;
q.push(edge(dist2[next],next));
}
}
}
}
int main()
{
int n,r;
cin>>n>>r;
int x,y,cost;
for(int i=0;i<r;++i)
{
cin>>x>>y>>cost;
node[x].push_back(edge(cost,y));//路是双向的
node[y].push_back(edge(cost,x));
}
dijkstra(1);
printf("%d\n",dist2[n]);
}