bzoj 3223: Tyvj 1729 文艺平衡树
Description
您需要写一种数据结构(可参考题目标题),来维护一个有序数列,其中需要提供以下操作:翻转一个区间,例如原有序序列是5 4 3 2 1,翻转区间是[2,4]的话,结果是5 2 3 4 1
Input
第一行为n,m n表示初始序列有n个数,这个序列依次是(1,2……n-1,n) m表示翻转操作次数
接下来m行每行两个数[l,r] 数据保证 1<=l<=r<=n
Output
输出一行n个数字,表示原始序列经过m次变换后的结果
Sample Input
5 3
1 3
1 3
1 4
1 3
1 3
1 4
Sample Output
4 3 2 1 5
HINT
N,M<=100000
![](https://images2015.cnblogs.com/blog/841250/201602/841250-20160226141502755-96597330.png)
头一回写SPLAY的翻转……不用考虑优先级什么的,翻[l,r]的时候就把l-1和r+1挪出来,中间那串就交换左右儿子就行了(其实位置就是key)
#include<cstdio> #include<cstdlib> #include<algorithm> using namespace std; int n,m,l,r,p,ch; inline int read(){ p=0;ch=getchar(); while(ch<'0'||ch>'9') ch=getchar(); while(ch>='0'&&ch<='9') p=p*10+ch-48,ch=getchar(); return p; } struct tree{ int l,r,k,f,s; bool bo; tree(){ bo=f=l=r=0; } }; struct splay_tree{ int size,root; tree t[100001]; splay_tree(){ size=0;root=0; } inline void ler(int &p){ int k=t[p].r; t[k].f=t[p].f; t[p].f=k; t[t[k].l].f=p; t[p].r=t[k].l; t[k].l=p; t[k].s=t[p].s; t[p].s=t[t[p].l].s+t[t[p].r].s+1; p=k; } inline void rir(int &p){ int k=t[p].l; t[k].f=t[p].f; t[p].f=k; t[t[k].r].f=p; t[p].l=t[k].r; t[k].r=p; t[k].s=t[p].s; t[p].s=t[t[p].l].s+t[t[p].r].s+1; p=k; } inline void ph(int &x,bool bo){ if (bo) rir(x);else ler(x); } inline bool getc(int x){ return t[t[x].f].l==x; } inline void rot(int l){ if (t[l].f==root) ph(root,getc(l));else if (getc(t[l].f)) ph(t[t[t[l].f].f].l,getc(l));else ph(t[t[t[l].f].f].r,getc(l)); } inline void splay(int l,int f){ while (t[l].f!=f){ if (t[t[l].f].f==f) rot(l);else if (getc(l)==getc(t[l].f)) rot(t[l].f),rot(l);else rot(l),rot(l); } } inline void build(int &p,int l,int r){ if (l>r) return; p=++size; int mid=(l+r)>>1; t[p].k=mid; build(t[p].l,l,mid-1); build(t[p].r,mid+1,r); t[t[p].l].f=t[t[p].r].f=p; t[p].s=1+t[t[p].l].s+t[t[p].r].s; } inline void pd(int x){ if (t[x].bo){ t[t[x].l].bo^=1;t[t[x].r].bo^=1; t[x].bo=0; swap(t[x].l,t[x].r); } } inline int find(int x,int y){ pd(x); if (t[t[x].l].s<y-1) return find(t[x].r,y-1-t[t[x].l].s); if (t[t[x].l].s==y-1) return x; return find(t[x].l,y); } inline void dfs(int x){ if (!x) return; pd(x); dfs(t[x].l);if (t[x].k!=0&&t[x].k<=n)printf("%d ",t[x].k);dfs(t[x].r); } }; splay_tree t; int main(){ n=read();m=read(); t.build(t.root,0,n+1); while(m--){ l=read();r=read(); l=t.find(t.root,l);r=t.find(t.root,r+2); t.splay(l,0);t.splay(r,l); t.t[t.t[r].l].bo^=1; } t.dfs(t.root); }