Chip FactoryTime Limit: 18000/9000 MS (Java/Others) Memory Limit: 262144/262144 K (Java/Others)Total Submission(s): 96 Accepted Submission(s): 51
Problem Description
John is a manager of a CPU chip factory, the factory produces lots of chips everyday. To manage large amounts of products, every processor has a serial number. More specifically, the factory produces
n
chips today, the
i
-th chip produced this day has a serial number
si
.
At the end of the day, he packages all the chips produced this day, and send it to wholesalers. More specially, he writes a checksum number on the package, this checksum is defined as below:
maxi,j,k(si+sj)⊕sk
which i,j,k are three different integers between 1 and n . And ⊕ is symbol of bitwise XOR. Can you help John calculate the checksum number of today?
Input
The first line of input contains an integer
T
indicating the total number of test cases.
The first line of each test case is an integer n , indicating the number of chips produced today. The next line has n integers s1,s2,..,sn , separated with single space, indicating serial number of each chip. 1≤T≤1000 3≤n≤1000 0≤si≤109 There are at most 10 testcases with n>100
Output
For each test case, please output an integer indicating the checksum number in a line.
Sample Input
Sample Output
|
题意:给定n个元素,让你从中任意选择三个元素a[i] a[j] a[k] 使得 (a[i] + a[j]) ^ a[k]最大。
思路:建立字典树,枚举a[i]和a[j],删除后,在Trie上查询a[i]+a[j]能够异或得到的最大值,然后恢复Trie,继续下次查询。
AC代码:
#include <cstdio>
#include <cstring>
#include <cmath>
#include <cstdlib>
#include <algorithm>
#include <queue>
#include <stack>
#include <vector>
#include <map>
#define MAXN 30100
#define LL long long
#define Ri(a) scanf("%d", &a)
#define Pi(a) printf("%d\n", (a))
#define Rl(a) scanf("%lld", &a)
#define Pl(a) printf("%lld\n", (a))
#define Rs(a) scanf("%s", a)
#define Ps(a) printf("%s\n", (a))
#define W(a) while(a--)
#define CLR(a, b) memset(a, (b), sizeof(a))
#define INF 0x3f3f3f3f
using namespace std;
struct Tree
{
int next[MAXN][2], word[MAXN];
int L, root;
int newnode()
{
for(int i = 0; i < 2; i++)
next[L][i] = -1;
word[L++] = 0;
return L-1;
}
void init()
{
L = 0;
root = newnode();
}
void Insert(int val)
{
int u = root, v;
for(int i = 30; i >= 0; i--)
{
v = (val & (1 << i)) ? 1 : 0;
if(next[u][v] == -1)
next[u][v] = newnode();
u = next[u][v];
word[u]++;
}
}
void Delete(int val)
{
int u = root, v;
for(int i = 30; i >= 0; i--)
{
v = (val & (1 << i)) ? 1 : 0;
u = next[u][v];
word[u]--;
}
}
int Query(int val)
{
int u = root, v;
for(int i = 30; i >= 0; i--)
{
v = (val & (1 << i)) ? 1 : 0;
if(v == 1)
{
if(next[u][0] != -1 && word[next[u][0]])
u = next[u][0];
else
u = next[u][1], val ^= (1 << i);
}
else
{
if(next[u][1] != -1 && word[next[u][1]])
u = next[u][1], val ^= (1 << i);
else
u = next[u][0];
}
}
return val;
}
};
Tree tree;
int a[1010];
int main()
{
int t; Ri(t);
W(t)
{
int n; Ri(n);
tree.init();
for(int i = 1; i <= n; i++)
scanf("%d", &a[i]), tree.Insert(a[i]);
int ans = 0;
for(int i = 1; i <= n; i++)
{
tree.Delete(a[i]);
for(int j = i+1; j <= n; j++)
{
tree.Delete(a[j]);
ans = max(ans, tree.Query(a[i]+a[j]));
tree.Insert(a[j]);
}
tree.Insert(a[i]);
}
Pi(ans);
}
return 0;
}