Nowcoder Practice 61 D.最短路变短了 (最短路)
题意:给定有向带权图,求将一条边反向是否使最短路变短。
思路:显然修改后若不走这条边最短路不会变短,若走这条路需要比较d[v]+w+d1[u]与d[n]的关系 (d[ i ]表示到1的距离,d1[ i ]表示到n的距离。
SPFA 链式
#include<bits/stdc++.h>
using namespace std;
#define mst(a) memset(a,0,sizeof a)
typedef long long ll;
const int N=1e5+5,M=2e5+5,inf=0x3f3f3f3f;
ll n,m,d[N],h[N],d1[N],vis[N],q,cnt=1;
struct edge{
ll to,nt,w;
}e[M];
ll a[M][3];
void add(int u,int v,ll w){
e[cnt].to=v;
e[cnt].w=w;
e[cnt].nt=h[u];
h[u]=cnt++;
}
void spfa(ll *dis,ll be){
queue<int>q;
for(int i=1;i<=n;i++) dis[i]=1e14,vis[i]=0;
//for(int i=1;i<=n;i++) printf("dis[%d]=%d\n",i,dis[i]);
q.push(be);
vis[be]=1;
dis[be]=0;
while(q.size()){
int u=q.front();q.pop();vis[u]=0;
for(int i=h[u];i;i=e[i].nt){
ll v=e[i].to,w=e[i].w;
if(dis[v]>dis[u]+w){
dis[v]=dis[u]+w;
if(!vis[v]) vis[v]=1,q.push(v);
}
}
}
}
int main(){
ios::sync_with_stdio(false),cin.tie(0);
cin>>n>>m;
for(int i=1;i<=m;i++){
for(int j=0;j<3;j++)
cin>>a[i][j];
add(a[i][0],a[i][1],a[i][2]);
}
spfa(d,1);
mst(h),cnt=1;
for(int i=1;i<=m;i++)
e[i].nt=0;
for(int i=1;i<=m;i++){
add(a[i][1],a[i][0],a[i][2]);
}
spfa(d1,n);
//for(int i=1;i<=n;i++) printf("d=%d,d1=%d\n",d[i],d1[i]);
cin>>q;
while(q--){
int x;
cin>>x;
if(d[a[x][1]]+a[x][2]+d1[a[x][0]]<d[n])
puts("YES");
else puts("NO");
}
return 0;
}
SPFA 邻接矩阵
#include<bits/stdc++.h>
using namespace std;
typedef long long ll;
#define PII pair<int,int>
const int N=1e5+5,M=2e5+5;
vector<PII >e[N],e1[N];
ll d[N],d1[N],u[M],v[M],c[M],n,m,q;
void spfa(int be,ll d[],vector<PII >e[]){
for(int i=1;i<=n;i++) d[i]=1e14;
d[be]=0;
queue<int>q;
q.push(be);
while(q.size()){
int u=q.front();q.pop();
for(auto it:e[u]){
int v=it.first,w=it.second;
if(d[v]>d[u]+w)
d[v]=d[u]+w,q.push(v);
}
}
}
int main(){
ios::sync_with_stdio(false),cin.tie(0);
cin>>n>>m;
for(int i=1;i<=m;i++){
cin>>u[i]>>v[i]>>c[i];
e[u[i]].push_back({v[i],c[i]});
e1[v[i]].push_back({u[i],c[i]});
}
spfa(1,d,e),spfa(n,d1,e1);
//for(int i=1;i<=n;i++) printf("%d,%d\n",d[i],d1[i]);
cin>>q;
while(q--){
int x;
cin>>x;
if(d[v[x]]+c[x]+d1[u[x]]<d[n])
puts("YES");
else puts("NO");
}
return 0;
}