이 제출은 이전 버전의 oj.uz에서 채점하였습니다. 현재는 제출 당시와는 다른 서버에서 채점을 하기 때문에, 다시 제출하면 결과가 달라질 수도 있습니다.
#include <bits/stdc++.h>
using namespace std;
using i32 = int;
using i64 = long long;
template <typename T>
using V = vector<T>;
template <typename T>
using VV = V<V<T>>;
template <typename T>
using VVV = V<VV<T>>;
template <typename T>
bool chmin(T &x, const T &y) {
if (x > y) {
x = y;
return true;
}
return false;
}
template <typename T>
bool chmax(T &x, const T &y) {
if (x < y) {
x = y;
return true;
}
return false;
}
#define OVERRIDE4(a, b, c, d, ...) d
#define REP2(i, n) for (i32 i = 0; i < (i32)(n); ++i)
#define REP3(i, l, r) for (i32 i = (i32)(l); i < (i32)(r); ++i)
#define REP(...) OVERRIDE4(__VA_ARGS__, REP3, REP2)(__VA_ARGS__)
#define PER2(i, n) for (i32 i = (i32)(n)-1; i >= 0; --i)
#define PER3(i, l, r) for (i32 i = (i32)(r)-1; i >= (i32)(l); --i)
#define PER(...) OVERRIDE4(__VA_ARGS__, PER3, PER2)(__VA_ARGS__)
#define ALL(x) begin(x), end(x)
#define LEN(x) (i32) size(x)
void dbg(i32 x) { cerr << x; }
void dbg(i64 x) { cerr << x; }
template <typename T, typename U>
void dbg(pair<T, U> p) {
cerr << '(';
dbg(p.first);
cerr << ", ";
dbg(p.second);
cerr << ')';
}
template <typename T>
void dbg(V<T> arr) {
cerr << '[';
REP(i, LEN(arr)) {
if (i) {
cerr << ", ";
}
dbg(arr[i]);
}
cerr << ']';
}
void debug() { cerr << '\n'; }
template <typename Head, typename... Tail>
void debug(Head head, Tail... tail) {
dbg(head);
cerr << ", ";
debug(tail...);
}
#ifdef DEBUGF
#define DBG(...) \
do { \
cerr << #__VA_ARGS__ << " : "; \
debug(__VA_ARGS__); \
} while (false)
#else
#define DBG(...) (void)0
#endif
#include <variant>
#include "islands.h"
VV<i32> scc(const VV<pair<i32, i32>> &g) {
i32 n = LEN(g);
VV<i32> ret;
V<i32> alive(n, 1), in(n, -1), ord(n, -1), stc;
auto dfs = [&](auto dfs, i32 v, i32 &t) -> void {
in[v] = ord[v] = t++;
stc.push_back(v);
for (auto [u, e] : g[v]) {
if (!alive[u]) {
continue;
}
if (in[u] == -1) {
dfs(dfs, u, t);
chmin(ord[v], ord[u]);
} else {
chmin(ord[v], in[u]);
}
}
if (in[v] == ord[v]) {
V<i32> comp;
while (true) {
comp.push_back(stc.back());
stc.pop_back();
alive[comp.back()] = 0;
if (comp.back() == v) {
break;
}
}
ret.push_back(comp);
}
};
i32 t = 0;
REP(i, n) {
if (in[i] == -1) {
dfs(dfs, i, t);
}
}
return ret;
}
variant<bool, V<i32>> find_journey(i32 n, i32 m, V<i32> u, V<i32> v) {
VV<pair<i32, i32>> g(n);
REP(i, m) { g[u[i]].emplace_back(v[i], i); }
if (n == 2) {
bool ok = (LEN(g[0]) >= 2 && LEN(g[1]) >= 1);
if (!ok) {
return false;
}
i32 e01a = g[0][0].second;
i32 e01b = g[0][1].second;
i32 e10 = g[1][0].second;
V<i32> walk({e01a, e10, e01b, e01a, e10, e01b});
return walk;
}
map<pair<i32, i32>, V<i32>> edgeid;
REP(i, m) { edgeid[pair<i32, i32>(u[i], v[i])].push_back(i); }
{
V<i32> revc;
REP(i, 1, n) {
if (edgeid.count(pair<i32, i32>(0, i)) &&
edgeid.count(pair<i32, i32>(i, 0))) {
revc.push_back(i);
}
}
if (LEN(revc) >= 2) {
i32 u = revc[0];
i32 v = revc[1];
i32 e01 = edgeid[pair<i32, i32>(0, u)][0];
i32 e10 = edgeid[pair<i32, i32>(u, 0)][0];
i32 e02 = edgeid[pair<i32, i32>(0, v)][0];
i32 e20 = edgeid[pair<i32, i32>(v, 0)][0];
V<i32> walk({e01, e10, e02, e20, e10, e01, e20, e02});
return walk;
}
}
bool is_subtask3 = true, is_subtask4 = true;
if (m % 2 == 0) {
REP(i, m / 2) {
if (u[2 * i] != v[2 * i + 1] || u[2 * i + 1] != v[2 * i]) {
is_subtask3 = false;
}
if (u[2 * i] != u[2 * i + 1] || v[2 * i + 1] != v[2 * i]) {
is_subtask4 = false;
}
}
} else {
is_subtask3 = is_subtask4 = false;
}
VV<i32> comps = scc(g);
DBG(comps);
V<i32> ccn(n);
REP(i, LEN(comps)) {
for (i32 v : comps[i]) {
ccn[v] = i;
}
}
V<i32> indeg(n, 0), outdeg(n, 0);
REP(v, n) {
for (auto [u, e] : g[v]) {
if (ccn[v] == ccn[u]) {
++indeg[u];
++outdeg[v];
}
}
}
V<i32> is_ok(n, 0), reach_cycle(n, 0);
for (const V<i32> &comp : comps) {
i32 reach_edge = 0;
for (i32 v : comp) {
for (auto [u, e] : g[v]) {
if (reach_cycle[u]) {
++reach_edge;
}
}
}
if (LEN(comp) >= 2 || reach_edge) {
for (i32 v : comp) {
reach_cycle[v] = 1;
}
}
if (reach_edge >= 2) {
for (i32 v : comp) {
is_ok[v] = 1;
}
continue;
}
bool outer = false;
for (i32 v : comp) {
for (auto [u, e] : g[v]) {
if (is_ok[u]) {
outer = true;
}
}
}
if (outer) {
for (i32 v : comp) {
is_ok[v] = 1;
}
continue;
}
bool deg3 = false;
for (i32 v : comp) {
if (outdeg[v] >= 3 && indeg[v] >= 2) {
deg3 = true;
}
if (outdeg[v] >= 2) {
is_ok[v] = 1;
}
}
if (deg3) {
for (i32 v : comp) {
is_ok[v] = 1;
}
}
}
bool exists = is_ok[0];
/*if (!exists) {
return false;
}*/
auto get_path = [&](i32 from, i32 to) -> V<i32> {
V<i32> dist(n, -1), pare(n, -1);
queue<i32> que;
dist[from] = 0;
que.push(from);
while (!que.empty()) {
i32 v = que.front();
que.pop();
for (auto [u, e] : g[v]) {
if (dist[u] == -1) {
dist[u] = dist[v] + 1;
pare[u] = e;
que.push(u);
}
}
}
V<i32> path;
while (to != from) {
i32 e = pare[to];
path.push_back(e);
to ^= u[e] ^ v[e];
}
reverse(ALL(path));
return path;
};
if (is_subtask3) {
if (!exists) {
return false;
}
i32 c = -1;
REP(i, n) {
if (LEN(g[i]) >= 3 && ccn[i] == ccn[0]) {
c = i;
}
}
assert(c != -1);
V<i32> path = get_path(0, c);
i32 last = path.back();
g[c].erase(
find(ALL(g[c]), pair<i32, i32>(u[last] ^ v[last] ^ c, last ^ 1)));
i32 e0 = g[c][0].second;
i32 e0b = e0 ^ 1;
i32 e1 = g[c][1].second;
i32 e1b = e1 ^ 1;
V<i32> ret = path;
ret.push_back(e0);
ret.push_back(e0b);
ret.push_back(e1);
ret.push_back(e1b);
ret.push_back(e0b);
ret.push_back(e0);
ret.push_back(e1b);
ret.push_back(e1);
PER(i, LEN(path)) { ret.push_back(path[i]); }
return ret;
}
auto get_simple_cycle = [&](i32 c) -> V<i32> {
V<i32> vis(n, 0), par(n, -1), pare(n, -1);
i32 back = -1, backe = -1;
auto dfs = [&](auto dfs, i32 v) -> void {
vis[v] = 1;
for (auto [u, e] : g[v]) {
if (ccn[u] != ccn[v]) {
continue;
}
if (u == c) {
back = v;
backe = e;
}
if (!vis[u]) {
par[u] = v;
pare[u] = e;
dfs(dfs, u);
}
}
};
dfs(dfs, c);
assert(back != -1);
DBG(back, backe, par, pare);
V<i32> cycle;
cycle.push_back(backe);
while (back != c) {
cycle.push_back(pare[back]);
back = par[back];
}
reverse(ALL(cycle));
return cycle;
};
if (is_subtask4) {
if (!exists) {
return false;
}
V<i32> dest(n, -1);
for (const V<i32> &comp : comps) {
if (LEN(comp) >= 2) {
for (i32 v : comp) {
dest[v] = v;
}
continue;
}
i32 pct = -1;
for (i32 v : comp) {
for (auto [u, e] : g[v]) {
if (dest[u] != -1) {
pct = dest[u];
}
}
}
for (i32 v : comp) {
dest[v] = pct;
}
}
i32 d0 = dest[0];
assert(d0 != -1);
DBG(d0);
V<i32> path = get_path(0, d0);
V<i32> cycle = get_simple_cycle(d0);
DBG(path, cycle);
V<i32> ret = path;
REP(i, 2) {
for (i32 e : cycle) {
ret.push_back(e ^ i);
}
}
REP(i, 2) {
PER(j, LEN(cycle)) {
ret.push_back(cycle[j] ^ i);
}
}
PER(i, LEN(path)) { ret.push_back(path[i]); }
return ret;
}
return exists;
}
# | 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... |
# | Verdict | Execution time | Memory | Grader output |
---|
Fetching results... |