hihocoder1860 最大异或和
Posted wangyiming
tags:
篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了hihocoder1860 最大异或和相关的知识,希望对你有一定的参考价值。
思路:
把N个前缀异或和插入一棵trie树中,然后对每个前缀异或和x计算能使x ^ y最大的前缀异或和y。利用了异或运算的a ^ b ^ a = b的性质。
参考了https://cloud.tencent.com/developer/article/1343206
实现:
1 #include <iostream> 2 using namespace std; 3 4 const int INF = 0x3f3f3f3f; 5 const int N = 100005; 6 int a[N], cnt = 0; 7 8 struct trieNode 9 { 10 trieNode * next[2]; 11 }; 12 13 trieNode pool[N * 32]; 14 15 trieNode * createTrie() 16 { 17 trieNode * root = &pool[cnt++]; 18 for (int i = 0; i < 2; i++) 19 { 20 root->next[i] = NULL; 21 } 22 return root; 23 } 24 25 void insert(trieNode * root, int x) 26 { 27 trieNode * tmp = root; 28 int index; 29 for (int i = 31; i >= 0; i--) 30 { 31 int msk = (1 << i); 32 if (msk & x) index = 1; 33 else index = 0; 34 if (tmp->next[index] == NULL) 35 { 36 tmp->next[index] = createTrie(); 37 } 38 tmp = tmp->next[index]; 39 } 40 } 41 42 int search(trieNode * root, int x) 43 { 44 trieNode * tmp = root; 45 int res = 0; 46 for (int i = 31; i >= 0; i--) 47 { 48 int msk = 1 << i; 49 int need; 50 if (msk & x) need = 0; 51 else need = 1; 52 if (i == 31) need = 1 - need; 53 if (tmp->next[need]) 54 { 55 res += (need << i); 56 tmp = tmp->next[need]; 57 } 58 else 59 { 60 res += (1 - need << i); 61 tmp = tmp->next[1 - need]; 62 } 63 } 64 return x ^ res; 65 } 66 67 int main() 68 { 69 int n; 70 while (cin >> n) 71 { 72 cnt = 0; 73 trieNode * root = createTrie(); 74 for (int i = 1; i <= n; i++) 75 { 76 cin >> a[i]; 77 a[i] = a[i - 1] ^ a[i]; 78 insert(root, a[i]); 79 } 80 insert(root, 0); 81 int ans = -INF; 82 for (int i = 1; i <= n; i++) 83 { 84 ans = max(ans, search(root, a[i])); 85 } 86 cout << ans << endl; 87 } 88 return 0; 89 }
以上是关于hihocoder1860 最大异或和的主要内容,如果未能解决你的问题,请参考以下文章