在此为LCT开一个永久的坑
2016-07-23 10:13
225 查看
其实我连splay都还不怎么会。
今天先抄了黄学长的bzoj2049,以后一定要把它理解了。
写LCT怎么能不%数据结构大神yeweining呢?%%%chrysanthemums %%%切掉大森林的全ZJ唯一一人
#include<cstdio> #include<algorithm> #define inf 2e9 #define N 500020 using namespace std; int u,v,a,b,n,m,rev ,ans=inf,stack ,val ,fa ,maxn ,f ,ch [2]; struct wxx{int u,v,a,b;}edge ; bool cmp(wxx a,wxx b){if(a.a==b.a)return a.b<b.b;return a.a<b.a;} int find(int x){if(fa[x]!=x)fa[x]=find(fa[x]);return fa[x];} bool isrt(int x){return ch[f[x]][0]!=x&&ch[f[x]][1]!=x;} int get(int x){return ch[f[x]][1]==x;} void update(int x){ if(x){ maxn[x]=x; if(ch[x][0]){ if(val[maxn[ch[x][0]]]>val[maxn[x]])maxn[x]=maxn[ch[x][0]]; } if(ch[x][1]){ if(val[maxn[ch[x][1]]]>val[maxn[x]])maxn[x]=maxn[ch[x][1]]; } } } void rotate(int x){ int yl=f[x],yf=f[yl],you=get(x); if(isrt(yl)==0)ch[yf][ch[yf][1]==yl]=x; f[x]=yf; ch[yl][you]=ch[x][you^1];f[ch[yl][you]]=yl; ch[x][you^1]=yl;f[yl]=x; update(yl);update(x); } void pushdown(int x){ if(x&&rev[x]){ swap(ch[x][0],ch[x][1]); if(ch[x][0])rev[ch[x][0]]^=1; if(ch[x][1])rev[ch[x][1]]^=1; rev[x]=0; } } void splay(int x){ int top=0;stack[++top]=x; for(int i=x;!isrt(i);i=f[i])stack[++top]=f[i]; for(int i=top;i>=1;i--)pushdown(stack[i]); for(int ff;isrt(x)==0;rotate(x)){ ff=f[x]; if(isrt(ff)==0) if(get(x)==get(ff))rotate(ff);else rotate(x); } } void access(int x){ int t=0; for (;x;t=x,x=f[x]){ splay(x); ch[x][1]=t; update(x); } } void reverse(int x){ access(x);splay(x);rev[x]^=1; } void link(int x,int y){ reverse(x);f[x]=y;splay(x); } void cut(int x,int y){ reverse(x);access(y);splay(y); ch[y][0]=f[x]=0; } int query(int x,int y){ reverse(x);access(y);splay(y); return maxn[y]; } int main() { scanf("%d%d",&n,&m); for(int i=1;i<=m;i++){ scanf("%d%d%d%d",&edge[i].u,&edge[i].v,&edge[i].a,&edge[i].b); } sort(edge+1,edge+m+1,cmp); for(int i=1;i<=m;i++)val[n+i]=edge[i].b; for(int i=1;i<=n;i++)fa[i]=i; for(int i=1;i<=m;i++){ int fx=find(edge[i].u),fy=find(edge[i].v); if(fx!=fy){ link(edge[i].u,n+i); link(n+i,edge[i].v); fa[fx]=fy; } else{ int k=query(edge[i].u,edge[i].v); if(val[k]>edge[i].b){ cut(edge[k-n].u,k); cut(k,edge[k-n].v); link(edge[i].u,n+i); link(n+i,edge[i].v); }} if(find(1)==find(n)){ int k=query(1,n); ans=min(ans,edge[i].a+val[k]); } } if(ans==inf)ans=-1;printf("%d\n",ans); }bzoj3669
相关文章推荐
- Linux下查看文件和文件夹大小
- 入职培训学习心得
- 集成Visual Studio/MSBuild的开发/发布流程和 FIS3
- Java 输入一个大写字母,如F 比如: 输入:F 输出: A ABA ABCBA ABCDCBA ABCDEDCBA ABCDEFEDCBA
- 计算平面中点间距离
- <30天自制操作系统>第五天
- Leetcode: N-Queens
- 大牛们的浓咖啡(Espresso)简单介绍
- 如何在Ubuntu13.10上安装Sublime Text 3
- php性能优化
- Viking Village维京村落demo中的地面积水效果
- Spring事务管理--(一)数据库事务隔离级别与mysql引擎基础讲解
- 进制转换
- 5. Longest Palindromic Substring
- django--app(六)
- 使用QProxyStyle定制QMenu (二)
- 计算机基础
- QT中自定义快捷键
- HDU(1010)bfs+剪枝 Tempter of the Bone
- 飞机大战