제출 #244345

#제출 시각아이디문제언어결과실행 시간메모리
244345pit4hOlympic Bus (JOI20_ho_t4)C++14
0 / 100
278 ms2452 KiB
#include<bits/stdc++.h> using namespace std; const int N = 201, M = 5e4+1; const int INF = 13e8+1; int n, m, u[M], v[M]; int c[M], d[M]; int G[N][N], W[N][N], E[N][N][2]; int skip[N][N][2], skipt[N][N][2]; // 0 -> (n, 1), 1 -> (1, n) void calculate_skip(int p, int q) { for(int i=1; i<=n; ++i) { for(int j=1; j<=n; ++j) { skip[i][j][p==1] = INF; } } //calc skip here for(int k=1; k<=n; ++k) { if(k==q) continue; vector<bool> vis(n+1); vis[k] = 1; priority_queue<pair<int, int>> Q; Q.push({0, q}); skip[q][k][p==1] = 0; while(Q.size()) { auto cur = Q.top(); cur.first *= -1; Q.pop(); if(vis[cur.second]) continue; vis[cur.second] = 1; for(int i=1; i<=n; ++i) { if(i==k) continue; if(skip[i][k][p==1] > cur.first + W[i][cur.second]) { Q.push({-(cur.first + W[i][cur.second]), i}); skip[i][k][p==1] = cur.first + W[i][cur.second]; } } } } for(int i=1; i<=n; ++i) { for(int j=1; j<=n; ++j) { skipt[i][j][p==1] = INF; } } //calc skip here for(int k=1; k<=n; ++k) { if(k==q) continue; vector<bool> vis(n+1); vis[k] = 1; priority_queue<pair<int, int>> Q; Q.push({0, q}); skipt[q][k][p==1] = 0; while(Q.size()) { auto cur = Q.top(); cur.first *= -1; Q.pop(); if(vis[cur.second]) continue; vis[cur.second] = 1; for(int i=1; i<=n; ++i) { if(i==k) continue; if(skipt[i][k][p==1] > cur.first + W[cur.second][i]) { Q.push({-(cur.first + W[cur.second][i]), i}); skipt[i][k][p==1] = cur.first + W[cur.second][i]; } } } } } int Dist(int U, bool q, int V) { if(!q && U == 1) return 0; if(q && U == n) return 0; int res = INF; for(int i=1; i<=n; ++i) { if(i != U && i != V) { res = min(res, W[U][i] + skip[i][U][q]); } } return res; } int DistT(int U, bool q, int V) { if(!q && U == 1) return 0; if(q && U == n) return 0; int res = INF; for(int i=1; i<=n; ++i) { if(i != U && i != V) { res = min(res, W[i][U] + skipt[i][U][q]); } } return res; } int solve(int p, int q) { int ans = INF; for(int i=0; i<m; ++i) { int path[2] = {0, 0}; // skipt[v[i]][u[i]][p==1] path[1] = DistT(v[i], p==1, u[i]) + c[i] + d[i] + Dist(u[i], p==n, v[i]); path[0] = INF; path[0] = min(path[0], DistT(v[i], p==n, u[i]) + c[i] + Dist(u[i], p==1, v[i])); int replace_edge = INF; if(E[u[i]][v[i]][0] != c[i]) { replace_edge = E[u[i]][v[i]][0]; path[0] = min(path[0], G[p][u[i]] + E[u[i]][v[i]][0] + G[v[i]][q]); } else { replace_edge = E[u[i]][v[i]][1]; path[0] = min(path[0], G[p][u[i]] + E[u[i]][v[i]][1] + G[v[i]][q]); } if(replace_edge < INF) replace_edge = max(0, replace_edge - c[i]); if(G[p][u[i]] + c[i] + G[v[i]][q] > G[p][q]) path[0] = min(path[0], G[p][q]); else { path[0] = min(path[0], skip[p][u[i]][p==1]); for(int k=1; k<=n; ++k) { if(k != u[i] && k != v[i]) { path[0] = min(path[0], G[p][u[i]] + W[u[i]][k] + skip[k][u[i]][p==1]); } } } path[0] = min(path[0], replace_edge + G[p][v[i]] + c[i] + G[u[i]][q]); path[1] = min(path[1], replace_edge + G[q][v[i]] + c[i] + d[i] + G[u[i]][p]); ans = min(ans, path[0] + path[1]); } return ans; } int main() { ios_base::sync_with_stdio(0); cin.tie(0); cout.tie(0); cin>>n>>m; for(int i=1; i<=n; ++i) { for(int j=1; j<=n; ++j) { G[i][j] = INF; W[i][j] = INF; E[i][j][0] = E[i][j][1] = INF; } G[i][i] = 0; } for(int i=0; i<m; ++i) { cin>>u[i]>>v[i]>>c[i]>>d[i]; G[u[i]][v[i]] = min(G[u[i]][v[i]], c[i]); W[u[i]][v[i]] = min(W[u[i]][v[i]], c[i]); if(E[u[i]][v[i]][0] > c[i]) { E[u[i]][v[i]][1] = E[u[i]][v[i]][0]; E[u[i]][v[i]][0] = c[i]; } else if(E[u[i]][v[i]][1] > c[i]) { E[u[i]][v[i]][1] = c[i]; } } for(int k=1; k<=n; ++k) { for(int i=1; i<=n; ++i) { for(int j=1; j<=n; ++j) { G[i][j] = min(G[i][j], G[i][k] + G[k][j]); } } } calculate_skip(1, n); calculate_skip(n, 1); int ans = min({G[1][n]+G[n][1], solve(1, n), solve(n, 1)}); if(ans >= INF) cout<<-1; else cout<<ans; }
#Verdict Execution timeMemoryGrader output
Fetching results...
#Verdict Execution timeMemoryGrader output
Fetching results...
#Verdict Execution timeMemoryGrader output
Fetching results...
#Verdict Execution timeMemoryGrader output
Fetching results...