QOJ.ac
QOJ
ID | 题目 | 提交者 | 结果 | 用时 | 内存 | 语言 | 文件大小 | 提交时间 | 测评时间 |
---|---|---|---|---|---|---|---|---|---|
#511071 | #3405. Exclusive-OR | PetroTarnavskyi# | AC ✓ | 54ms | 3784kb | C++20 | 2.6kb | 2024-08-09 15:52:02 | 2024-08-09 15:52:02 |
Judging History
answer
#include <bits/stdc++.h>
using namespace std;
#define FOR(i, a, b) for(int i = (a); i < (b); i++)
#define RFOR(i, a, b) for(int i = (a) - 1; i >= (b); i--)
#define SZ(a) int(a.size())
#define ALL(a) a.begin(), a.end()
#define PB push_back
#define MP make_pair
#define F first
#define S second
typedef long long LL;
typedef vector<int> VI;
typedef pair<int, int> PII;
typedef double db;
int n, Q;
struct DSU
{
int n;
VI p, sz;
VI xr, val;
void init(int _n)
{
n = _n;
p.resize(n);
iota(ALL(p), 0);
sz.assign(n, 1);
xr.assign(n, 0);
val.assign(n, -1);
}
PII find(int v)
{
if (v == p[v])
return {v, xr[v]};
PII res = find(p[v]);
return {res.F, res.S ^ xr[v]};
}
bool unite(int u, int v, int x)
{
PII U = find(u);
PII V = find(v);
u = U.F;
v = V.F;
if (u == v)
return (U.S ^ V.S) == x;
if (sz[u] > sz[v])
swap(u, v);
p[u] = v;
xr[u] = x ^ U.S ^ V.S;
sz[v] += sz[u];
if (val[u] != -1 && val[v] != -1 && (val[u] ^ xr[u]) != val[v])
return false;
if (val[u] != -1 && val[v] == -1)
val[v] = val[u] ^ xr[u];
return true;
}
};
void solve()
{
DSU d;
d.init(n);
int cnt = 0;
string s;
getline(cin, s);
bool ok = true;
FOR (i, 0, Q)
{
getline(cin, s);
if (!ok)
continue;
stringstream ss(s);
char c;
ss >> c;
int x;
VI v;
while (ss >> x)
v.PB(x);
if (c == 'I')
{
cnt++;
if (SZ(v) == 2)
{
int p = v[0];
int val = v[1];
auto res = d.find(p);
if (d.val[res.F] == -1)
d.val[res.F] = val ^ res.S;
if (d.val[res.F] != (val ^ res.S))
{
cout << "The first " << cnt << " facts are conflicting.\n";
ok = false;
}
}
else
{
assert(SZ(v) == 3);
int p = v[0];
int q = v[1];
int val = v[2];
ok &= d.unite(p, q, val);
if (!ok)
{
cout << "The first " << cnt << " facts are conflicting.\n";
}
}
}
else
{
assert(c == 'Q');
int xr = 0;
map<int, int> mp;
FOR (j, 0, v[0])
{
int p = v[j + 1];
PII res = d.find(p);
mp[res.F]++;
xr ^= res.S;
}
bool know = true;
for (auto [p, ch] : mp)
{
if (ch & 1)
{
if (d.val[p] == -1)
know = false;
else
xr ^= d.val[p];
}
}
if (!know)
cout << "I don't know.\n";
else
cout << xr << '\n';
}
}
}
int main()
{
ios::sync_with_stdio(0);
cin.tie(0);
for (int tc = 1; ; tc++)
{
cin >> n >> Q;
if (n == 0)
break;
cout << "Case " << tc << ":\n";
solve();
cout << '\n';
}
return 0;
}
详细
Test #1:
score: 100
Accepted
time: 54ms
memory: 3784kb
input:
5 12 I 0 1 4 I 2 3 3 I 4 5 Q 5 0 4 3 1 2 I 3 4 7 Q 1 3 Q 1 2 I 0 2 17 Q 1 0 Q 2 0 1 I 0 3 6 Q 1 2 5 14 I 0 1 4 I 2 3 3 I 4 5 Q 5 0 4 3 1 2 I 3 4 7 Q 1 3 Q 1 2 Q 3 0 1 3 I 0 2 17 I 4 5 I 0 5 Q 1 0 Q 2 0 1 Q 1 2 5 14 I 0 1 345 I 0 2 72 I 0 3 723 Q 3 1 2 3 Q 2 1 3 I 3 634 Q 3 1 2 3 Q 2 1 3 Q 1 4 Q 1 0 ...
output:
Case 1: 2 2 1 16 4 The first 6 facts are conflicting. Case 2: 2 2 1 6 The first 7 facts are conflicting. Case 3: I don't know. 906 875 906 I don't know. 169 496 225 634 440 Case 4: I don't know. I don't know. I don't know. I don't know. I don't know. 1058 24209 I don't know. I don't know. I don't...
result:
ok 13459 lines