CF888G Xor-MST[最小生成树+01trie]
前注:关于这题,本人的解法暂时没有成功通过此题,原因是被卡常了。可能需要等待某种机缘来请人调试。
类似uoj的一道题(新年的繁荣),不过是一个有些简单的版本。
因为是完全图,有没有办法明显优化建边,所以考虑用这个Boruvka算法。MST学习笔记里应当记下来了,可以自行前往。然后在这里,就发现使用Boruvka的话明显就有了可以优化的地方——每个点向外找一条最小的边。这里,因为异或的特殊性,所以可以想到用01trie来查找xor最小值。于是boruvka就与数据结构结合起来了。然后照着流程做即可。
不过注意一个问题:每轮连通块内的点找trie上最小异或值,可能会找到块内的点(甚至自己),所以要避免,这里可以对于每个子树,维护一个min,max,代表子树内叶子代表的点所在的块编号的最大最小值,于是查找的时候就可以提前判断,避免走入不合法的地方。
但是被卡常了。。2s时限,跑了2.6左右。。难受。。等待救援。咕咕。
#pragma comment(linker,"/STACK:102400000,102400000")
#pragma GCC optimize("Ofast")
#pragma GCC optimize("inline")
#pragma GCC optimize("-fgcse")
#pragma GCC optimize("-fgcse-lm")
#pragma GCC optimize("-fipa-sra")
#pragma GCC optimize("-ftree-pre")
#pragma GCC optimize("-ftree-vrp")
#pragma GCC optimize("-fpeephole2")
#pragma GCC optimize("-ffast-math")
#pragma GCC optimize("-fsched-spec")
#pragma GCC optimize("unroll-loops")
#pragma GCC optimize("-falign-jumps")
#pragma GCC optimize("-falign-loops")
#pragma GCC optimize("-falign-labels")
#pragma GCC optimize("-fdevirtualize")
#pragma GCC optimize("-fcaller-saves")
#pragma GCC optimize("-fcrossjumping")
#pragma GCC optimize("-fthread-jumps")
#pragma GCC optimize("-funroll-loops")
#pragma GCC optimize("-fwhole-program")
#pragma GCC optimize("-freorder-blocks")
#pragma GCC optimize("-fschedule-insns")
#pragma GCC optimize("inline-functions")
#pragma GCC optimize("-ftree-tail-merge")
#pragma GCC optimize("-fschedule-insns2")
#pragma GCC optimize("-fstrict-aliasing")
#pragma GCC optimize("-fstrict-overflow")
#pragma GCC optimize("-falign-functions")
#pragma GCC optimize("-fcse-skip-blocks")
#pragma GCC optimize("-fcse-follow-jumps")
#pragma GCC optimize("-fsched-interblock")
#pragma GCC optimize("-fpartial-inlining")
#pragma GCC optimize("no-stack-protector")
#pragma GCC optimize("-freorder-functions")
#pragma GCC optimize("-findirect-inlining")
#pragma GCC optimize("-fhoist-adjacent-loads")
#pragma GCC optimize("-frerun-cse-after-loop")
#pragma GCC optimize("inline-small-functions")
#pragma GCC optimize("-finline-small-functions")
#pragma GCC optimize("-ftree-switch-conversion")
#pragma GCC optimize("-foptimize-sibling-calls")
#pragma GCC optimize("-fexpensive-optimizations")
#pragma GCC optimize("-funsafe-loop-optimizations")
#pragma GCC optimize("inline-functions-called-once")
#pragma GCC optimize("-fdelete-null-pointer-checks")
#include<iostream>
#include<cstdio>
#include<cstring>
#include<algorithm>
#include<cmath>
#include<queue>
#define dbg(x) cerr << #x << " = " << x <<endl
#define dbg2(x,y) cerr<< #x <<" = "<< x <<" "<< #y <<" = "<< y <<endl
using namespace std;
typedef long long ll;
typedef double db;
typedef pair<int,int> pii;
template<typename T>inline T _min(T A,T B){return A<B?A:B;}
template<typename T>inline T _max(T A,T B){return A>B?A:B;}
template<typename T>inline char MIN(T&A,T B){return A>B?(A=B,):;}
template<typename T>inline char MAX(T&A,T B){return A<B?(A=B,):;}
template<typename T>inline void _swap(T&A,T&B){A^=B^=A^=B;}
template<typename T>inline T read(T&x){
x=;int f=;char c;while(!isdigit(c=getchar()))if(c=='-')f=;
while(isdigit(c))x=x*+(c&),c=getchar();return f?x=-x:x;
}
const int N=2e5+,INF=0x3f3f3f3f;
int len,n,thxorz;
int A[N];
int anc[N];
inline int get_anc(int x){return anc[x]==x?x:anc[x]=get_anc(anc[x]);}
struct _01trie{
int tr[N*][],maxv[N*],minv[N*],id[N*],tot;
_01trie(){maxv[]=,minv[]=INF;}
inline void Insert(int x,int j){//dbg2(x,j);
int u=;
for(register int i=len,d;~i;--i){
if(!tr[u][d=(x>>i)&])tr[u][d]=++tot;
u=tr[u][d];
}
id[u]=j;
}
void Maintain(int i){//++thxorz;
if(!tr[i][]&&!tr[i][]){maxv[i]=minv[i]=get_anc(id[i]);return;}
if(tr[i][])Maintain(tr[i][]);
if(tr[i][])Maintain(tr[i][]);
maxv[i]=_max(maxv[tr[i][]],maxv[tr[i][]]);
minv[i]=_min(minv[tr[i][]],minv[tr[i][]]);//dbg2(i,tr[i][0]),dbg2(minv[i],maxv[i]);
}
inline void Build(){for(register int i=;i<=n;++i)Insert(A[i],i);}
inline int Query(int x,int j){
int u=,rt=get_anc(j);//dbg2(rt,x);
for(register int i=len,d;~i;--i){//++thxorz;
d=(x>>i)&;//dbg2(d,tr[u][d]),dbg2(maxv[tr[u][d]],minv[tr[u][d]]);
if(tr[u][d]&&(maxv[tr[u][d]]^rt||minv[tr[u][d]]^rt))u=tr[u][d];
else u=tr[u][d^];
}//dbg(id[u]);
return id[u];
}
}T;
int minw[N],minp[N];
inline void Boruvka(){
int k=;ll ans=;
T.Build();
for(register int i=;i<=n;++i)anc[i]=i;
while(k<n-){//dbg("new round");
T.maxv[]=,T.minv[]=INF,T.Maintain();memset(minw,0x7f,sizeof minw);
for(register int i=,tmp;i<=n;++i)tmp=T.Query(A[i],i),MIN(minw[get_anc(i)],A[tmp]^A[i])&&(minp[anc[i]]=tmp);
for(register int i=;i<=n;++i)if(get_anc(i)^get_anc(minp[get_anc(i)]))
ans+=minw[anc[i]],++k,anc[anc[i]]=anc[minp[anc[i]]];//attention the order.
}
printf("%I64d\n",ans);
} int main(){//freopen("test.in","r",stdin);//freopen("test.ans","w",stdout);
read(n);for(register int i=;i<=n;++i)MAX(len,read(A[i]));
len=__lg(len);
Boruvka();//dbg(thxorz);
return ;
}

CF888G Xor-MST[最小生成树+01trie]的更多相关文章
- MST最小生成树
首先,贴上一个很好的讲解贴: http://www.wutianqi.com/?p=3012 HDOJ 1233 还是畅通工程 http://acm.hdu.edu.cn/showproblem.ph ...
- [BZOJ1937][SHOI2004]Mst最小生成树(KM算法,最大费用流)
1937: [Shoi2004]Mst 最小生成树 Time Limit: 3 Sec Memory Limit: 64 MBSubmit: 802 Solved: 344[Submit][Sta ...
- 【BZOJ1937】[Shoi2004]Mst 最小生成树 KM算法(线性规划)
[BZOJ1937][Shoi2004]Mst 最小生成树 Description Input 第一行为N.M,其中 表示顶点的数目, 表示边的数目.顶点的编号为1.2.3.…….N-1.N.接下来的 ...
- [poj1679]The Unique MST(最小生成树)
The Unique MST Time Limit: 1000MS Memory Limit: 10000K Total Submissions: 28207 Accepted: 10073 ...
- UVA 1151 Buy or Build (MST最小生成树,kruscal,变形)
题意: 要使n个点之间能够互通,要使两点直接互通需要耗费它们之间的欧几里得距离的平方大小的花费,这说明每两个点都可以使其互通.接着有q个套餐可以选,一旦选了这些套餐,他们所包含的点自动就连起来了,所需 ...
- MST最小生成树及克鲁斯卡尔(Kruskal)算法
最小生成树MST,英文名如何拼写已忘,应该是min spaning tree吧.假设一个无向连通图有n个节点,那么它的生成树就是包括这n个节点的无环连通图,无环即形成树.最小生成树是对边上权重的考虑, ...
- MST最小生成树及Prim普鲁姆算法
MST在前面学习了Kruskal算法,还有一种算法叫做Prim的.这两者的区别是Prim算法适合稠密图,比如说鸟巢这种几乎所有点都有相连的图.其时间复杂度为O(n^2),其时间复杂度与边的数目无关:而 ...
- 【KM】BZOJ1937 [Shoi2004]Mst 最小生成树
这道题拖了好久因为懒,结果1A了,惊讶∑( 口 || [题目大意] 给定一张n个顶点m条边的有权无向图.现要修改各边边权,使得给出n-1条边是这张图的最小生成树,代价为变化量的绝对值.求最小代价之和. ...
- Prim求MST最小生成树
最小生成树即在一个图中用最小权值的边将所有点连接起来.prim算法求MST其实它的主要思路和dijkstra的松弛操作十分相似 prim算法思想:在图中随便找一个点开始这里我们假定起点为“1”,以点1 ...
随机推荐
- 关于bootstrap的响应式插件respond.min.js在IE8下出现:拒绝访问。respond.min.js,行: 5,列: 746报错问题
本地在IE8浏览器下测试兼容性的时候,出现了以下的报错: 该问题在bootstrap的官网有介绍:https://v3.bootcss.com/getting-started
- Linux:shift 命令可以将参数依次向左移动一个位置
在脚本中,命令行参数可以依据其在命令行中的位置来访问.第一个参数是 $1 ,第二个参数 是 $2 ,以此类推. 下面的语句可以显示出前3个命令行参数: echo $1 $2 $3 更为常见的处理方式是 ...
- 【LOJ】#3042. 「ZJOI2019」麻将
LOJ#3042. 「ZJOI2019」麻将 如何判定一个集合牌有没有胡的子集是不是胡的 就用一个\(dp[j][k][0/1]\)表示有j个连续两个的串,有k个连续1个串,有没有对子,再记一下这个集 ...
- Javascript去掉base64中的回车换行
给天津海关开发手机插件. 他们的API返回的文件base64遵循了RFC822规定,即BASE64编码每76个字符,还需要加上一个回车换行. 这就导致了我的Ant Design Mobile图片控件不 ...
- 关于php性能优化
php性能优化 1.尽量静态化: 如果一个方法能被静态,那就声明它为静态的,速度可提高1/4,甚至我测试的时候,这个提高了近三倍. 当然了,这个测试方法需要在十万级以上次执行,效果才明显. 其实静态方 ...
- Java回调实现异步 (转)
出处: Java回调实现异步 在正常的业务中使用同步线程,如果服务器每处理一个请求,就创建一个线程的话,会对服务器的资源造成浪费.因为这些线程可能会浪费时间在等待网络传输,等待数据库连接等其他事情上, ...
- 服务端相关知识学习(二)之Zookeeper可以干什么
Zookeeper主要可以干哪些事情 配置管理,名字服务,提供分布式同步以及集群管理.那这些服务又到底是什么呢?我们为什么需要这样的服务?我们又为什么要使用Zookeeper来实现呢,使用Zookee ...
- VLC播放各种源
RTSP rtsp://admin:Shws1610@192.168.1.33:554/channel/01 UDP 播放推导本机上的udp流 : udp://@:1234 播放其他机器上的ud ...
- 【ExtJs】在Ext.grid.Panel中,两列的值相乘作为第三列的值的实现
如: 商品总价=商品单价*商品数量 方法: 商品总价列,使用其renderer属性,为期定义一个方法,该方法将当前record中的另外两列中2个数据相乘后渲染到该商品总价列.
- js数据类型的转换
类型转换:就是把一种数据类型转换成另一种数据类型,在js中类型转换有以下三种情况:转数字,转字符串,转布尔值.对象转成这3种数据类型是没有意义的,对象里面可以放任意的数据类型. 在讲解类型转换之前,先 ...