This submission is migrated from previous version of oj.uz, which used different machine for grading. This submission may have different result if resubmitted.
#include <bits/stdc++.h>
using namespace std;
const int MM = 205,MV = 5e4+5;
typedef pair<int64_t,array<int,2>> Node;
int n,m; int64_t dist[MM][MV],ans; vector<array<int,3>> adj[MM]; vector<array<int,4>> bk[MM];
array<int,4> el[MV];
int main(){
cin.tie(0)->sync_with_stdio(0);
cin >> n >> m; ans = 1e18;
for(int i = 1; i <= m; i++){
int a,b,c,d; cin >> a >> b >> c >> d;
el[i] = {a,b,c,d};
adj[a].push_back({b,c,i});
bk[b].push_back({a,c,d,i});
}
// took reverse edge first time on 1-n
{
memset(dist,0x3f,sizeof dist);
priority_queue<Node,vector<Node>,greater<>> q;
for(int i = 0; i <= m; i++) dist[1][i] = el[i][3],q.push({0,{1,i}});
while(q.size()){
auto[d,tmp] = q.top(); q.pop();
auto[u,i] = tmp;
if(d > dist[u][i]) continue;
// take regular edge
for(auto[v,w,j]:adj[u]){
if(j == i) continue; // flipped, original dir doesn't work
if(dist[v][i] > dist[u][i] + w){
dist[v][i] = dist[u][i]+w;
q.push({dist[v][i],{v,i}});
}
}
// try taking back edge
for(auto[v,w,c,j]:bk[u])if(j == i){
if(dist[v][i] > dist[u][i]+w){
dist[v][i] = dist[u][i]+w;
q.push({dist[v][i],{v,i}});
}
}
}
for(int j = 0; j <= m; j++){
if(dist[n][j] > 2e9) continue;
q.push({dist[n][j],{n,j}});
}
for(int i = 1; i < n; i++){
memset(dist[i],0x3f,sizeof dist[i]);
}
while(q.size()){
auto[d,tmp] = q.top(); q.pop();
auto[u,i] = tmp;
if(d > dist[u][i]) continue;
// take regular edge
for(auto[v,w,j]:adj[u]){
if(j == i) continue; // flipped, original dir doesn't work
if(dist[v][i] > dist[u][i] + w){
dist[v][i] = dist[u][i]+w;
q.push({dist[v][i],{v,i}});
}
}
// try taking back edge
for(auto[v,w,c,j]:bk[u])if(j == i){
if(dist[v][i] > dist[u][i]+w){
dist[v][i] = dist[u][i]+w;
q.push({dist[v][i],{v,i}});
}
}
}
for(int i = 0; i <= m; i++) ans = min(ans,dist[1][i]);
}
// took reverse edge first time on n-1
{
memset(dist,0x3f,sizeof dist);
priority_queue<Node,vector<Node>,greater<>> q;
for(int i = 0; i <= m; i++) dist[n][i] = el[i][3],q.push({0,{n,i}});
while(q.size()){
auto[d,tmp] = q.top(); q.pop();
auto[u,i] = tmp;
if(d > dist[u][i]) continue;
// take regular edge
for(auto[v,w,j]:adj[u]){
if(j == i) continue; // flipped, original dir doesn't work
if(dist[v][i] > dist[u][i] + w){
dist[v][i] = dist[u][i]+w;
q.push({dist[v][i],{v,i}});
}
}
// try taking back edge
for(auto[v,w,c,j]:bk[u])if(j == i){
if(dist[v][i] > dist[u][i]+w){
dist[v][i] = dist[u][i]+w;
q.push({dist[v][i],{v,i}});
}
}
}
for(int j = 0; j <= m; j++){
if(dist[1][j] > 2e9) continue;
q.push({dist[1][j],{1,j}});
}
for(int i = 2; i <= n; i++){
memset(dist[i],0x3f,sizeof dist[i]);
}
while(q.size()){
auto[d,tmp] = q.top(); q.pop();
auto[u,i] = tmp;
if(d > dist[u][i]) continue;
// take regular edge
for(auto[v,w,j]:adj[u]){
if(j == i) continue; // flipped, original dir doesn't work
if(dist[v][i] > dist[u][i] + w){
dist[v][i] = dist[u][i]+w;
q.push({dist[v][i],{v,i}});
}
}
// try taking back edge
for(auto[v,w,c,j]:bk[u])if(j == i){
if(dist[v][i] > dist[u][i]+w){
dist[v][i] = dist[u][i]+w;
q.push({dist[v][i],{v,i}});
}
}
}
for(int i = 0; i <= m; i++) ans = min(ans,dist[n][i]);
}
cout << (ans > 2e9 ? -1 : 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... |