P3391 【模板】文艺平衡树
2019-11-27 16:58 一只弱鸡丶 阅读(114) 评论(0) 编辑 收藏 举报#include <bits/stdc++.h> using namespace std; #define ll long long #define re register const int N=1e6+10; void read(int &a) { a=0;int d=1;char ch; while(ch=getchar(),ch>'9'||ch<'0') if(ch=='-') d=-1; a=ch^48; while(ch=getchar(),ch>='0'&&ch<='9') a=(a<<3)+(a<<1)+(ch^48); a*=d; } struct note{int ch[2],siz,tag,cnt,val,fa;}spl[N]; int rt,cnt,n,m; void newnode(int &now,int fa,int val) { spl[now=++cnt].val=val; spl[now].siz=spl[now].cnt=1; spl[now].fa=fa; spl[now].tag=0; } int ident(int x,int f){return spl[f].ch[1]==x;}///判断是否为右儿子 void connect(int x,int f,int s) { spl[f].ch[s]=x; spl[x].fa=f; } void update(int now){spl[now].siz=spl[spl[now].ch[0]].siz+spl[spl[now].ch[1]].siz+1;} void rotat(int x) { int f=spl[x].fa,ff=spl[f].fa,k=ident(x,f); connect(spl[x].ch[k^1],f,k); connect(x,ff,ident(f,ff)); connect(f,x,k^1); update(f),update(x); } void splaying(int x,int top)///把x转到top的儿子 { if(!top) rt=x; while(spl[x].fa!=top) { int f=spl[x].fa,ff=spl[f].fa; if(ff!=top) ident(f,ff)^ident(x,f)?rotat(x):rotat(f); rotat(x); } } void ins(int val,int &now=rt,int fa=0) { if(!now) newnode(now,fa,val),splaying(now,0); else if(spl[now].val>val) ins(val,spl[now].ch[0],now); else if(spl[now].val<val) ins(val,spl[now].ch[1],now); else spl[now].siz++,splaying(now,0); } inline void pushdown(int x) { if(spl[x].tag) { spl[spl[x].ch[0]].tag^=1; spl[spl[x].ch[1]].tag^=1; spl[x].tag=0; swap(spl[x].ch[0],spl[x].ch[1]); } } int getv(int k) { int v=rt; while(1) { pushdown(v); if(spl[spl[v].ch[0]].siz>=k)v=spl[v].ch[0]; else if(spl[spl[v].ch[0]].siz+1==k) return v; else k-=spl[spl[v].ch[0]].siz+1,v=spl[v].ch[1]; } } void rever(int l,int r) { l=getv(l);r=getv(r+2); splaying(l,0),splaying(r,l); spl[spl[spl[rt].ch[1]].ch[0]].tag^=1; } void ldr(int now) { pushdown(now); if(!now) return; ldr(spl[now].ch[0]); if(spl[now].val>1&&spl[now].val<n+2) printf("%d ",spl[now].val-1); ldr(spl[now].ch[1]); } int main() { read(n),read(m); for(re int i=1;i<=n+2;i++) ins(i,rt); for(re int i=1,x,y;i<=m;i++) read(x),read(y),rever(x,y); ldr(rt); return 0; }