异或最大值【字典树】
1216: 异或最大值
Submit Page Summary Time Limit: 2 Sec Memory Limit: 128 Mb Submitted: 1374 Solved: 503
Description
给定一些数,求这些数中两个数的异或值最大的那个值
Input
多组数据。第一行为数字个数n,1 <= n <= 10 ^ 5。接下来n行每行一个32位有符号非负整数。
Output
任意两数最大异或值
Sample Input
3
3
7
9
Sample Output
14
思路:
像是一个模板题但是里面用到了:
1.题目是要求在已知的数组选出异或后结果最大的 可以想象两个数其中一定有一个是数组中的最大值
2.异或符号在电脑中的使用
具体讲解可以看下另一篇博客:
https://blog.csdn.net/weixin_43350051/article/details/88085514
AC代码:
数组忘记初始化了 但也A了
#include<bits/stdc++.h>
using namespace std;
const int MAX=1e5;
int maxx=-MAX;
int top;
int tir[MAX+5][5],num[MAX+5];
int a[MAX+5],b[MAX+5];
void add(int *a)
{
int root=0;
for(int i=31;i>=0;i--){
int id=a[i];
if(tir[root][id]==0){
tir[root][id]=++top;
}
root=tir[root][id];
}
}
int find(int *b)
{
int root=0,count=0;
for(int i=31;i>=0;i--){
int id=b[i];
if(tir[root][id]==0){
if(id==0){
id=1;
}
else{
id=0;
}
}
if(tir[root][id]==0){
break;
}
num[count++]=id;
root=tir[root][id];
}
int sum=0,count1=1;
for(int i=count-1;i>=0;i--){
sum+=num[i]*count1;
count1*=2;
}
return sum^maxx;
}
int main()
{
int m,n;
while(~scanf("%d",&n)){
for(int i=0;i<n;i++){
scanf("%d",&m);
maxx=max(maxx,m);
for(int i=31;i>=0;i--){
a[i]=m&(1<<i)?1:0;
}
add(a);
}
for(int i=31;i>=0;i--){
b[i]=maxx&(1<<i)?0:1;
}
int sum=find(b);
printf("%d\n",sum);
return 0;
}
}