题目大意
给出一个图, 个点, 条边的无向图
给出一个
若 为0,则输出1~n的最短路
若 为1,则输出1~n的次短路
题目解析
用 算法,使用邻接表优化一下
首先以 和 为起点做一遍单源最短路
然后枚举每一条边 ,求出起点到 终点到 边 权值之和,若不等于 最短路长度则更新
代码
#include<bits/stdc++.h>
using namespace std;
int n,m,u,v,w,p,pos,ans=1e9;
int dis[2][10005],x[50005],y[50005],z[50005];
bool flag[10005];
vector<int> a[10005],b[10005];
queue<int> q;
int main()
{
cin>>n>>m;
for(int i=1;i<=m;i++)
{
cin>>u>>v>>w;
x[i]=u;y[i]=v;z[i]=w;
a[u].push_back(v);
b[u].push_back(w);
a[v].push_back(u);
b[v].push_back(w);
}
cin>>p;
memset(dis,0x3f,sizeof(dis));
dis[0][1]=dis[1][n]=0;
flag[1]=1;
q.push(1);
while(!q.empty())
{
pos=q.front(),q.pop();
flag[pos]=0;
for(int i=0;i<a[pos].size();i++)
{
if(dis[0][pos]+b[pos][i]<dis[0][a[pos][i]])
{
dis[0][a[pos][i]]=dis[0][pos]+b[pos][i];
if(!flag[a[pos][i]])
{
q.push(a[pos][i]);
flag[a[pos][i]]=1;
}
}
}
}
flag[1]=n;
q.push(n);
while(!q.empty())
{
pos=q.front(),q.pop();
flag[pos]=0;
for(int i=0;i<a[pos].size();i++)
{
if(dis[1][pos]+b[pos][i]<dis[1][a[pos][i]])
{
dis[1][a[pos][i]]=dis[1][pos]+b[pos][i];
if(!flag[a[pos][i]])
{
q.push(a[pos][i]);
flag[a[pos][i]]=1;
}
}
}
}
if(!p)
cout<<dis[0][n];
else
{
for(int i=1;i<=m;i++)
{
if(dis[0][x[i]]+z[i]+dis[1][y[i]]!=dis[0][n])
ans=min(ans,dis[0][x[i]]+z[i]+dis[1][y[i]]);
if(dis[0][y[i]]+z[i]+dis[1][x[i]]!=dis[0][n])
ans=min(ans,dis[0][y[i]]+z[i]+dis[1][x[i]]);
}
cout<<ans;
}
}