acwing 143. 最大异或对
题面:
在给定的N个整数A1,A2……ANA1,A2……AN中选出两个进行xor(异或)运算,得到的结果最大是多少?
输入格式
第一行输入一个整数N。
第二行输入N个整数A1A1~ANAN。
输出格式
输出一个整数表示答案。
数据范围
1≤N≤1051≤N≤105,
0≤Ai<2310≤Ai<231
输入样例:
3
1 2 3
输出样例:
3
题解:
异或性质+前缀+字典树
这道题目很难想到是字典树,如果不是放在字典树单元的话.
其实来说,一个整数,是可以转化成为一个32位的二进制数,而也就可以变成长度为32位的二进制字符串.
既然如此话,那么我们可以这么做,每一次检索的时候,我们都走与当前AiAi这一位相反的位置走,也就是让Xor值最大,如果说没有路可以走的话,那么就走相同的路.
代码:
#include<iostream> #include<cstring> #include<algorithm> using namespace std; int a[100010]; int son[3000100][2],idx; void insert(int x) { int p=0; for(int i=30;i>=0;i--) { int &s=son[p][x>>i&1]; if(!s)s=++idx; p=s; } } int query(int x) { int res=0,p=0; for(int i=30;i>=0;i--) { int s=x>>i&1; if(son[p][!s]) { p=son[p][!s]; res+=1<<i; } else p=son[p][s]; } return res; } int main() { int n;scanf("%d",&n); for(int i=0;i<n;i++) { scanf("%d",&a[i]); insert(a[i]); } int res=0; for(int i=0;i<n;i++)res=max(res,query(a[i])); cout<<res<<endl; return 0; }