Birthday Gift
我们将
我们从高位到低位枚举最高的一位与
我们先考虑更高位置如何相同
如果更高位置为
比如在枚举的时候,我们第一次枚举到一个
注意我们将每一组的所有数字都删除掉了,并形成一个新组,新组的每一个数字是原来对应组所有数字的异或(可见代码)
接下来我们考虑更低位的时候,我们分组就要满足上面的限制,比如如果我们要把四个
就相当于合并新数组的
如果更高位置为
主要是学习中间的决策包容性,以及不会遗漏最优解的操作
#include <bits/stdc++.h>
using namespace std;
using ll = long long;
#define int ll
#define all(a) a.begin(), a.end()
void solve() {
int n, x;
cin >> n >> x;
++x;
vector<int> a(n);
for (int &i: a)
cin >> i;
int res = -1;
for (int i = 30; i >= 0; --i) {
vector<int> b;
bool open = false;//为1表示有奇数个1,为0表示有偶数个1
for (int j = 0; j < a.size(); ++j) {
if (!open)
b.push_back(a[j]);
else
b.back() ^= a[j];
if (a[j] & (1 << i))
open = !open;
}//尝试模拟一下这个循环,就是分组用的
if (!(x & (1 << i))) {//如果这一位是0
if (open) {//这一位有奇数个1
//无论怎么分组最后这一位都会为1,大于0
//我们又认为更高位都相同,所以不用往下循环了
cout << res << '\n';
return;
}
a = b;//替换掉合并分组后的数组
} else {//如果这一位为1
if (!open)//这里就是不会遗漏最优解的原因
//可以想一下
res = max(res, (int) b.size());
}
}
cout << res << '\n';
}
signed main() {
ios_base::sync_with_stdio(false);
cin.tie(nullptr);
int t = 1;
cin >> t;
while (t--)
solve();
}
【推荐】国内首个AI IDE,深度理解中文开发场景,立即下载体验Trae
【推荐】编程新体验,更懂你的AI,立即体验豆包MarsCode编程助手
【推荐】抖音旗下AI助手豆包,你的智能百科全书,全免费不限次数
【推荐】轻量又高性能的 SSH 工具 IShell:AI 加持,快人一步
· TypeScript + Deepseek 打造卜卦网站:技术与玄学的结合
· 阿里巴巴 QwQ-32B真的超越了 DeepSeek R-1吗?
· 【译】Visual Studio 中新的强大生产力特性
· 10年+ .NET Coder 心语 ── 封装的思维:从隐藏、稳定开始理解其本质意义
· 【设计模式】告别冗长if-else语句:使用策略模式优化代码结构