Submission #538044

#TimeUsernameProblemLanguageResultExecution timeMemory
538044pavementSwapping Cities (APIO20_swap)C++17
100 / 100
429 ms69872 KiB
#include "swap.h" #include <bits/stdc++.h> #include <ext/pb_ds/assoc_container.hpp> #include <ext/pb_ds/tree_policy.hpp> using namespace std; using namespace __gnu_pbds; #ifdef _WIN32 #define getchar_unlocked _getchar_nolock #endif //#define int long long #define mp make_pair #define mt make_tuple #define pb push_back #define ppb pop_back #define eb emplace_back #define g0(a) get<0>(a) #define g1(a) get<1>(a) #define g2(a) get<2>(a) #define g3(a) get<3>(a) mt19937 rng(chrono::steady_clock::now().time_since_epoch().count()); typedef double db; typedef long long ll; typedef long double ld; typedef pair<int, int> ii; typedef tuple<int, int, int> iii; typedef tuple<int, int, int, int> iiii; typedef tree<ii, null_type, less<ii>, rb_tree_tag, tree_order_statistics_node_update> ordered_set; int N, M, dep[300005], link[100005], rep[100005], sz[100005], ep[100005][2], anc[300005][25]; bool nc[300005]; iii T[200005]; vector<int> U, V, W, adj[300005]; int find(int x) { if (x == link[x]) return x; return link[x] = find(link[x]); } void unite(int a, int b) { int u = a, v = b; a = find(a); b = find(b); if (a == b) return; if (sz[b] > sz[a]) swap(a, b); sz[a] += sz[b]; link[b] = a; nc[a] |= nc[b]; if (!nc[a]) { if (u == ep[a][0] && v == ep[b][0]) { ep[a][0] = ep[a][1]; ep[a][1] = ep[b][1]; } else if (u == ep[a][0] && v == ep[b][1]) { ep[a][0] = ep[a][1]; ep[a][1] = ep[b][0]; } else if (u == ep[a][1] && v == ep[b][0]) { ep[a][1] = ep[b][1]; } else if (u == ep[a][1] && v == ep[b][1]) { ep[a][1] = ep[b][0]; } else { swap(u, v); if (u == ep[a][0] && v == ep[b][0]) { ep[a][0] = ep[a][1]; ep[a][1] = ep[b][1]; } else if (u == ep[a][0] && v == ep[b][1]) { ep[a][0] = ep[a][1]; ep[a][1] = ep[b][0]; } else if (u == ep[a][1] && v == ep[b][0]) { ep[a][1] = ep[b][1]; } else if (u == ep[a][1] && v == ep[b][1]) { ep[a][1] = ep[b][0]; } else { nc[a] = 1; } } } } void dfs(int n, int e = -1) { anc[n][0] = e; for (int i = 1; i <= 20; i++) if (anc[n][i - 1] != -1) anc[n][i] = anc[anc[n][i - 1]][i - 1]; for (auto u : adj[n]) if (u != e) { dep[u] = dep[n] + 1; dfs(u, n); } } int lca(int u, int v) { if (dep[u] < dep[v]) swap(u, v); for (int i = 20; i >= 0; i--) if (dep[u] - (1 << i) >= dep[v]) u = anc[u][i]; if (u == v) return u; for (int i = 20; i >= 0; i--) if (anc[u][i] != anc[v][i]) { u = anc[u][i]; v = anc[v][i]; } return anc[u][0]; } void init(int _N, int _M, vector<int> _U, vector<int> _V, vector<int> _W) { N = _N; M = _M; U = _U; V = _V; W = _W; memset(anc, -1, sizeof anc); for (int i = 0; i < M; i++) T[i] = mt(W[i], U[i], V[i]); for (int i = 0; i < N; i++) { link[i] = rep[i] = ep[i][0] = ep[i][1] = i; sz[i] = 1; } sort(T, T + M); for (int i = 0; i < M; i++) { tie(W[i], U[i], V[i]) = T[i]; int a = rep[find(U[i])], b = rep[find(V[i])]; if (a != b) { adj[N + i].pb(a); adj[N + i].pb(b); } else { nc[find(U[i])] = 1; adj[N + i].pb(a); } unite(U[i], V[i]); nc[N + i] = nc[find(U[i])]; rep[find(U[i])] = N + i; } dfs(N + M - 1); } int getMinimumFuelCapacity(int X, int Y) { int w = lca(X, Y); if (nc[w]) return W[w - N]; for (int i = 20; i >= 0; i--) if (anc[w][i] != -1 && !nc[anc[w][i]]) w = anc[w][i]; if (anc[w][0] == -1) return -1; w = anc[w][0]; return W[w - N]; }
#Verdict Execution timeMemoryGrader output
Fetching results...
#Verdict Execution timeMemoryGrader output
Fetching results...
#Verdict Execution timeMemoryGrader output
Fetching results...
#Verdict Execution timeMemoryGrader output
Fetching results...
#Verdict Execution timeMemoryGrader output
Fetching results...
#Verdict Execution timeMemoryGrader output
Fetching results...