#include <bits/stdc++.h>
using namespace std;
using ll = long long;
using pii = pair <int, int>;
void boost() {
ios_base::sync_with_stdio(0);
cin.tie(0);
cout.tie(0);
}
int n, q, a, b, ids[300007], cnt;
int parent[1500007], d[1500007], val[1500007], removed[1500007];
char c;
string result;
int my_find(int a) {
if (parent[a] != a)
parent[a] = my_find(parent[a]);
return parent[a];
}
int my_union(int a, int b) {
if (d[a] < d[b])
swap(a, b);
d[a] += d[b];
removed[a] += removed[b];
parent[b] = a;
return a;
}
void add_edge() {
cin >> a >> b;
a = my_find(ids[a]);
b = my_find(ids[b]);
if (a == b) {
val[a] = 1;
return;
}
if (val[a] != 1 && val[b] != 1) {
val[my_union(a, b)] = -1;
}
else {
val[my_union(a, b)] = 1;
}
}
void remove_vertex() {
cin >> a;
b = my_find(ids[a]);
int removed_old = removed[b];
if (removed_old + 2 >= d[b] && val[b] == -1)
val[b] = 0;
removed[b] = removed_old + 1;
ids[a] = ++cnt;
parent[ids[a]] = ids[a];
d[ids[a]] = 1;
val[ids[a]] = 0;
}
char answer() {
cin >> a;
int v = val[my_find(ids[a])];
if (v == 0)
return '0';
if (v == 1)
return '1';
return '?';
}
int main() {
boost();
cin >> n >> q;
for (int i = 1; i <= n; i++) {
ids[i] = ++cnt;
parent[ids[i]] = ids[i];
d[ids[i]] = 1;
val[ids[i]] = 0;
}
while (q--) {
cin >> c;
if (c == '+')
add_edge();
if (c == '-')
remove_vertex();
if (c == '?')
result += answer();
}
cout << result << "\n";
return 0;
}
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 | #include <bits/stdc++.h> using namespace std; using ll = long long; using pii = pair <int, int>; void boost() { ios_base::sync_with_stdio(0); cin.tie(0); cout.tie(0); } int n, q, a, b, ids[300007], cnt; int parent[1500007], d[1500007], val[1500007], removed[1500007]; char c; string result; int my_find(int a) { if (parent[a] != a) parent[a] = my_find(parent[a]); return parent[a]; } int my_union(int a, int b) { if (d[a] < d[b]) swap(a, b); d[a] += d[b]; removed[a] += removed[b]; parent[b] = a; return a; } void add_edge() { cin >> a >> b; a = my_find(ids[a]); b = my_find(ids[b]); if (a == b) { val[a] = 1; return; } if (val[a] != 1 && val[b] != 1) { val[my_union(a, b)] = -1; } else { val[my_union(a, b)] = 1; } } void remove_vertex() { cin >> a; b = my_find(ids[a]); int removed_old = removed[b]; if (removed_old + 2 >= d[b] && val[b] == -1) val[b] = 0; removed[b] = removed_old + 1; ids[a] = ++cnt; parent[ids[a]] = ids[a]; d[ids[a]] = 1; val[ids[a]] = 0; } char answer() { cin >> a; int v = val[my_find(ids[a])]; if (v == 0) return '0'; if (v == 1) return '1'; return '?'; } int main() { boost(); cin >> n >> q; for (int i = 1; i <= n; i++) { ids[i] = ++cnt; parent[ids[i]] = ids[i]; d[ids[i]] = 1; val[ids[i]] = 0; } while (q--) { cin >> c; if (c == '+') add_edge(); if (c == '-') remove_vertex(); if (c == '?') result += answer(); } cout << result << "\n"; return 0; } |
English