Educational Codeforces Round 32 - G. Xor-MST ( 01字典树 + 分治 )
题目链接:点击进入
题目
题意
给你 n 个点的值,n 个点加边生成一棵树,边权就是两点的异或值,要求最后所有边权和最小。输出最小边权和。
思路
将 n 个数插入到01字典树上,对于树上的每个节点,记录这个节点保存有原数组的那些数(就是原数组中有哪些数经过这个节点),因为这些数可能在原数组中是无序的所以不好保存,因此我们可以将原数组排序后再插入字典树,这样每个节点所保存的数就是连续的,也就是每个节点只记录这个连续区间的边界即可。
遍历01字典树,
对于两个孩子的节点,左右孩子代表的区间是不同的,代表未连接的两个集合(这里默认两个集合内部已经连接好了),连接这两个集合,最好的肯定是只用一条边将两个集合连起来,这条边肯定是两边所代表的区间内的数互相异或的最小值。因此我们可以枚举左子树所代表的所有数,对于每个数,在右子树上贪心求异或最小值,将所有枚举左子树得到的最小值取最小就是连接两个集合的最小代价。然后递归继续解决左右子树。
对于单个孩子的节点,只有一个集合,继续递归解决。
对于没有孩子的节点,递归返回。
最后将递归过程中的所有最小代价相加就是最终答案。
代码
//#pragma GCC optimize(3)//O3
//#pragma GCC optimize(2)//O2
#include
#include
#include
评论列表(0条)