首先根据 \(\operatorname{xor}\),就想到拆成二进制的 \(a_{i, w}, b_{i, w}\) 来处理。
类似竖式加法,考虑把得到的结果 \(c_{w}\) 分为 \(a_{i, w} + b_{j, w} + x\),其中 \(x\) 就是上一位的进位。
进一步的,发现对于总的 \(c_{w}\),\(a_{i, w}, b_{j, w}\) 肯定都在这个位置加了 \(n\) 次,相当于是固定的。
于是就只需要考虑上一位往这一位进位多少次即可。
然后考虑如果 \(w\) 位向 \(w + 1\) 位进位有什么条件。
手玩一下能整理出来以下条件:
- 存在 \(p(p\le w)\),\(a_{i, p} = b_{j, p} = 1\),相当于首先要有进位。
- \(\forall x\in (p, w]\),\(a_{i, x} + b_{j, x} = 1\),相当于这个进位在向前传递。
对于条件 2,因为 \(a_{i, x} + b_{j, x} = 1\),就相当于是 \(a_{i, x} \operatorname{xor} b_{j, x} = 1\),那么就说明 \((p, w]\) 这些位 \(a_i, b_j\) 异或起来得到的就是 \(\operatorname{lim} = \sum\limits_{i = p + 1}^w 2^i\)。
那么就可以反过来用 \(\operatorname{lim}\operatorname{xor} a_i\) 去计数 \(b_j\) 了。
时间复杂度 \(\mathcal{O}(n\log^2 V)\),\(V\) 为值域。
计数的时候需要用个 Hash,常数有点大,需要卡卡常。
#include<bits/extc++.h>
const int maxn = 2e5 + 10, logV = 28;
int a[maxn][logV], b[maxn][logV];
int av[maxn], bv[maxn];
int c[logV + 1];
int main() {
int n; scanf("%d", &n);
for (int i = 1, x; i <= n; i++) {
scanf("%d", &x);
for (int w = 0; w < logV; w++) a[i][w] = x & (1 << w);
}
for (int i = 1, x; i <= n; i++) {
scanf("%d", &x);
for (int w = 0; w < logV; w++) b[i][w] = x & (1 << w);
}
for (int i = 1; i <= n; i++)
for (int w = 0; w < logV; w++) c[w] ^= (a[i][w] && (n & 1)) << w;
for (int i = 1; i <= n; i++)
for (int w = 0; w < logV; w++) c[w] ^= (b[i][w] && (n & 1)) << w;
std::unordered_map<int, int> mp;
for (int j = 0; j < logV; j++) {
memset(av, 0, sizeof(av)), memset(bv, 0, sizeof(bv));
std::vector<int> A, B;
for (int i = 1; i <= n; i++)
if (a[i][j]) A.push_back(i);
for (int i = 1; i <= n; i++)
if (b[i][j]) B.push_back(i);
c[j + 1] ^= ((A.size() & 1) && (B.size() & 1)) << j + 1;
int lim = 0;
for (int k = j + 1; k < logV; k++) {
lim |= 1 << k;
mp.clear();
for (int i : A) mp[lim ^ (av[i] |= a[i][k])] ^= 1;
int tot = 0;
for (int i : B) tot ^= mp[bv[i] |= b[i][k]];
c[k + 1] ^= tot << k + 1;
}
}
int ans = 0;
for (int i = 0; i <= logV; i++) ans += c[i];
printf("%d\n", ans);
return 0;
}
标签:logV,Atcoder,xor,int,operatorname,maxn,Sequences,ABC091D,进位
From: https://www.cnblogs.com/rizynvu/p/18281712