이 제출은 이전 버전의 oj.uz에서 채점하였습니다. 현재는 제출 당시와는 다른 서버에서 채점을 하기 때문에, 다시 제출하면 결과가 달라질 수도 있습니다.
#include <bits/stdc++.h>
using namespace std;
#define pii pair<long,int>
#define piii pair<long,pair<int,int>>
const int Nlim=1e5,Mlim=2e6,Vlim=1e9;
const long INF=(long)Mlim*Vlim+1;
int N,M,S,T,U,V;
vector<pii>conn[Nlim];
long Sdist[Nlim],Udist[Nlim],Vdist[Nlim];
long dp_U[Nlim],dp_V[Nlim];
bool visit[Nlim];
void dijkstra(int start,long dist[]){
for(int i=0; i<N; i++)dist[i]=INF;
priority_queue<pii,vector<pii>,greater<pii>>PQ;
dist[start]=0;
PQ.push({0,start});
while(!PQ.empty()){
long dd=PQ.top().first;
int node=PQ.top().second;
PQ.pop();
if(dist[node]!=dd)continue;//updated by someone else already
for(auto edge:conn[node]){
long w=edge.first;
int nd=edge.second;
if(dist[nd]>dist[node]+w){
dist[nd]=dist[node]+w;
PQ.push({dist[nd],nd});
}
}
}
}
void dijkstra_dp(int start,int end,long dist[]){
for(int i=0; i<N; i++){
dist[i]=dp_U[i]=dp_V[i]=INF;
visit[i]=0;
}
priority_queue<piii,vector<piii>,greater<piii>>PQ;
dist[start]=0;
PQ.push({0,{start,start}});//cumulative distance, node, parent
while(!PQ.empty()){
long dd=PQ.top().first;
int node=PQ.top().second.first,parent=PQ.top().second.second;
PQ.pop();
if(!visit[node]){
visit[node]=1;
dist[node]=dd;
for(auto edge:conn[node]){
long w=edge.first;
int nd=edge.second;
PQ.push({dd+w,{nd,node}});
}
dp_U[node]=min(Udist[node],dp_U[parent]);
dp_V[node]=min(Vdist[node],dp_V[parent]);
}
else if(dist[node]==dd){//alternative but equally good route
long uu=min(Udist[node],dp_U[parent]);
long vv=min(Vdist[node],dp_V[parent]);
//we check if the parent is better or not
//we can't just update one of the DPs as we either choose to use this route or don't
if(dp_U[node]+dp_V[node]>=uu+vv){//makes the answer better makes the route better
dp_U[node]=uu;
dp_V[node]=vv;
}
}
}
//cout<<dp_U[end]+dp_V[end]<<'\n';
}
int main(){
cin>>N>>M;
cin>>S>>T;
cin>>U>>V;
S--,T--,U--,V--;
for(int i=0; i<M; i++){
int a,b,c;
cin>>a>>b>>c;
a--,b--;
conn[a].push_back({c,b});
conn[b].push_back({c,a});//undirected
}
dijkstra(U,Udist);
dijkstra(V,Vdist);
long ans=Udist[V];
//cout<<Udist[V]<<'\n';
//construct dp_U, dp_U[i]=min distance from U to an arbitrary someone within S->i
//dp_U[i]=min(Udist[i],dp_U[i.parent]) I.E. shortest to i vs previous shortest till i.parent
//construct dp_V similarly
dijkstra_dp(S,T,Sdist);
ans=min(ans,dp_U[T]+dp_V[T]);
dijkstra_dp(T,S,Sdist);//undirected so we also check the opposite direction
ans=min(ans,dp_U[S]+dp_V[S]);
cout<<ans<<'\n';
}
# | Verdict | Execution time | Memory | Grader output |
---|
Fetching results... |
# | Verdict | Execution time | Memory | Grader output |
---|
Fetching results... |
# | Verdict | Execution time | Memory | Grader output |
---|
Fetching results... |
# | Verdict | Execution time | Memory | Grader output |
---|
Fetching results... |