[2019杭电多校第五场][hdu6625]three arrays(01字典树)
Posted sainsist
tags:
篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了[2019杭电多校第五场][hdu6625]three arrays(01字典树)相关的知识,希望对你有一定的参考价值。
题目链接:http://acm.hdu.edu.cn/showproblem.php?pid=6625
大意为给你两个数组a和b,对应位置异或得到c数组,现在可以将a,b数组从新排序求c数组,使得字典序最小。
大致的做法就是用两个数组中的数字二进制 建两颗字典树,同时记录每个位置的个数。然后在两颗字典树上同时dfs,优先往0-0和1-1方向走,不能走再走0-1,1-0方向。
因为0-0和1-1两种情况不分先后,所以走出来的不一定是最小的,走完得到的c数组要排序。
1 #include<iostream> 2 #include<cstdio> 3 #include<cstring> 4 #include<string> 5 #include<algorithm> 6 using namespace std; 7 typedef long long ll; 8 const int maxn = 100000 + 5; 9 struct Trie 10 int tree[maxn * 30][2], num[maxn * 30]; 11 int len, root; 12 int newcode() 13 tree[len][0] = tree[len][1] = 0; 14 num[len] = 0; 15 return len++; 16 17 void init() 18 len = 0; 19 root = newcode(); 20 21 void insert(int x) 22 int now = root; 23 for (int i = 29; i >= 0; i--) 24 int k = (x >> i) & 1; 25 if (!tree[now][k]) 26 tree[now][k] = newcode(); 27 now = tree[now][k]; 28 num[now]++; 29 30 31 A, B; 32 int ans[maxn]; 33 void slove(int n) 34 for (int i = 1; i <= n; i++) 35 ans[i] = 0; 36 int nowA = 0, nowB = 0; 37 for (int j = 29; j >= 0; j--) 38 if (A.num[A.tree[nowA][0]] && B.num[B.tree[nowB][0]]) 39 nowA = A.tree[nowA][0], nowB = B.tree[nowB][0]; 40 A.num[nowA]--, B.num[nowB]--; 41 42 else if (A.num[A.tree[nowA][1]] && B.num[B.tree[nowB][1]]) 43 nowA = A.tree[nowA][1], nowB = B.tree[nowB][1]; 44 A.num[nowA]--, B.num[nowB]--; 45 46 else if (A.num[A.tree[nowA][0]] && B.num[B.tree[nowB][1]]) 47 nowA = A.tree[nowA][0], nowB = B.tree[nowB][1]; 48 A.num[nowA]--, B.num[nowB]--; 49 ans[i] += (1 << j); 50 51 else if (A.num[A.tree[nowA][1]] && B.num[B.tree[nowB][0]]) 52 nowA = A.tree[nowA][1], nowB = B.tree[nowB][0]; 53 A.num[nowA]--, B.num[nowB]--; 54 ans[i] += (1 << j); 55 56 57 58 59 int main() 60 int t; 61 scanf("%d", &t); 62 while (t--) 63 int n, x; 64 A.init(), B.init(); 65 scanf("%d", &n); 66 for (int i = 1; i <= n; i++) 67 scanf("%d", &x), A.insert(x); 68 for (int i = 1; i <= n; i++) 69 scanf("%d", &x), B.insert(x); 70 slove(n); 71 sort(ans + 1, ans + 1 + n); 72 for (int i = 1; i <= n; i++) 73 printf("%d%c", ans[i], i == n ? ‘\n‘ : ‘ ‘); 74 75 76
以上是关于[2019杭电多校第五场][hdu6625]three arrays(01字典树)的主要内容,如果未能解决你的问题,请参考以下文章
[2019杭电多校第五场][hdu6624]fraction
[2019杭电多校第五场][hdu6628]permutation 1
[2019杭电多校第五场][hdu6629]string matching