Submission #604949

#TimeUsernameProblemLanguageResultExecution timeMemory
604949pakhomoveeOne-Way Streets (CEOI17_oneway)C++17
100 / 100
228 ms38016 KiB
#include <iostream> #include <string> #include <vector> #include <map> #include <algorithm> #include <iomanip> #include <unordered_set> #pragma GCC optimize("unroll-loops") #pragma GCC optimize("O2") using namespace std; int timer = 0; int timer1 = 0; bool IS_BRIDGE[200000]; void dfs(int v, int p, vector<bool>& used, vector<vector<pair<int, int>>>& g, vector<int>& tin, vector<int>& up) { tin[v] = timer++; up[v] = tin[v]; used[v] = true; for (pair<int, int> x : g[v]) { int u = x.first; int i = x.second; if (!used[u]) { dfs(u, v, used, g, tin, up); up[v] = min(up[v], up[u]); if (up[u] > tin[v]) { IS_BRIDGE[i] = true; } } else if (u != p) { up[v] = min(up[v], tin[u]); } } } void dfs1(int v, vector<int>& used, vector<vector<pair<int, int>>>& g, int cnt) { used[v] = cnt; for (pair<int, int> x : g[v]) { int u = x.first; int i = x.second; if (!IS_BRIDGE[i] && !used[u]) { dfs1(u, used, g, cnt); } } } int par[17][100000]; int h[100000]; void dfs2(int v, int p, vector<bool>& used, vector<int>& tin, vector<int>& tout, vector<vector<int>>& g) { used[v] = true; par[0][v] = p; if (p == v) h[v] = 0; else h[v] = h[p] + 1; for (int i = 1; i < 17; ++i) { par[i][v] = par[i - 1][par[i - 1][v]]; } tin[v] = timer1++; for (int u : g[v]) { if (!used[u]) { dfs2(u, p, used, tin, tout, g); } } tout[v] = timer1++; } bool ok(int a, int b, vector<int>& tin, vector<int>& tout) { if (tin[a] <= tin[b] && tout[a] >= tout[b]) return true; return false; } int get_lca(int a, int b, vector<int>& tin, vector<int>& tout) { for (int i = 16; i >= 0; --i) { if (!ok(par[i][a], b, tin, tout)) { a = par[i][a]; } } a = par[0][a]; return a; } void dfs3(int v, vector<bool>& used, vector<vector<int>>& g, vector<int>& lol, int w) { h[v] = w; used[v] = true; for (int u : g[v]) { if (!used[u]) { dfs3(u, used, g, lol, w + 1); lol[v] += lol[u]; } } } signed main() { ios_base::sync_with_stdio(false); cin.tie(0); cout.tie(0); int n, m; cin >> n >> m; for (int i = 0; i < m; ++i) { IS_BRIDGE[i] = false; } vector<vector<pair<int, int>>> g(n); vector<int> ans(m, 0); map<pair<int, int>, int> d; vector<pair<int, int>> e; for (int i = 0; i < m; ++i) { int u, v; cin >> u >> v; --u; --v; e.push_back({ u, v }); if (u > v) swap(u, v); if (d.count({ u, v })) { ans[d[{u, v}]] = -1; } d[{u, v}] = i; g[u].push_back({ v, i }); g[v].push_back({ u, i }); } vector<bool> used(n, false); vector<int> tin(n), up(n); for (int i = 0; i < n; ++i) { if (!used[i]) { dfs(i, -1, used, g, tin, up); } } for (int i = 0; i < m; ++i) { if (IS_BRIDGE[i] && ans[i] == -1) { IS_BRIDGE[i] = false; } if (!IS_BRIDGE[i]) { ans[i] = -1; } //cout << IS_BRIDGE[i] << ' '; } vector<vector<int>> g1(n); vector<int> used1(n, 0); int cnt = 1; for (int i = 0; i < n; ++i) { if (!used1[i]) { dfs1(i, used1, g, cnt++); } } for (int i = 0; i < n; ++i) { --used1[i]; } g1.resize(cnt - 1); for (int i = 0; i < n; ++i) { for (pair<int, int> x : g[i]) { int u = x.first; int j = x.second; if (IS_BRIDGE[j]) { g1[used1[i]].push_back(used1[u]); g1[used1[u]].push_back(used1[i]); } } } vector<bool> used2(cnt, false); vector<int> tout(cnt); vector<int> lol(cnt, 0); tin.resize(cnt); for (int i = 0; i < cnt - 1; ++i) { if (!used2[i]) { dfs2(i, 0, used2, tin, tout, g1); } } int p; cin >> p; for (int i = 0; i < p; ++i) { int u, v; cin >> u >> v; --u; --v; u = used1[u]; v = used1[v]; lol[u] += -1; lol[v] += 1; } used2.assign(cnt, false); for (int i = 0; i < cnt - 1; ++i) { if (!used2[i]) { dfs3(i, used2, g1, lol, 0); } } for (int i = 0; i < m; ++i) { int u = e[i].first; int v = e[i].second; u = used1[u]; v = used1[v]; //cout << i << ' ' << u << ' ' << v << ' ' << lol[u] << ' ' << lol[v] << endl; if ((h[u] > h[v] && lol[u] != 0) || (h[v] > h[u] && lol[v] != 0)) { if (h[u] > h[v] && lol[u] < 0) { ans[i] = 1; } else if (h[u] > h[v] && lol[u] > 0) { ans[i] = 2; } else if (h[u] < h[v] && lol[v] < 0) { ans[i] = 2; } else if (h[u] < h[v] && lol[v] > 0) { ans[i] = 1; } } else { ans[i] = -1; } } for (int i : ans) { if (i == -1) { cout << 'B'; } else if (i == 1) { cout << 'R'; } else { cout << 'L'; } } }
#Verdict Execution timeMemoryGrader output
Fetching results...
#Verdict Execution timeMemoryGrader output
Fetching results...
#Verdict Execution timeMemoryGrader output
Fetching results...