标签:bst splay 二叉树 namespace 序列维护
对序列进行m次操作,每次将[L,R]区间翻转后移到尾部。
提取区间之后翻转,分裂,进行两次合并
代码:
/************************************************************************* > File Name: Spaly.cpp > Author: acvcla > QQ: > Mail: acvcla@gmail.com > Created Time: 2014Äê11ÔÂ16ÈÕ ÐÇÆÚÈÕ 00ʱ14·Ö26Ãë ************************************************************************/ #include<iostream> #include<algorithm> #include<cstdio> #include<vector> #include<cstring> #include<map> #include<queue> #include<stack> #include<string> #include<cstdlib> #include<ctime> #include<set> #include<math.h> using namespace std; typedef long long LL; const int maxn = 2e5 + 100; const int inf=1e9+7; #define rep(i,a,b) for(int i=(a);i<=(b);i++) #define pb push_back int ch[maxn][2],pre[maxn],rev[maxn],siz[maxn]; int root,tot; int key[maxn]; void newnode(int &x,int fa,int k) { x=++tot; key[x]=k; siz[x]=1; pre[x]=fa; rev[x]=ch[x][1]=ch[x][0]=0; } void push_up(int x){ if(!x)return; siz[x]=siz[ch[x][0]]+siz[ch[x][1]]+1; } void upadte_rev(int x) { if(!x)return ; swap(ch[x][0],ch[x][1]); rev[x]^=1; } void push_down(int x) { if(!x)return; if(rev[x]){ upadte_rev(ch[x][0]); upadte_rev(ch[x][1]); rev[x]^=1; } } void Rotate(int x,int kind) { int y=pre[x]; push_down(y); push_down(x); ch[y][!kind]=ch[x][kind]; pre[ch[x][kind]]=y; ch[x][kind]=y; if(pre[y])ch[pre[y]][ch[pre[y]][1]==y]=x; pre[x]=pre[y]; pre[y]=x; push_up(y); push_up(x); } void Splay(int x,int goal) { while(pre[x]!=goal){ if(pre[pre[x]]==goal)Rotate(x,ch[pre[x]][0]==x); else{ int y=pre[x]; int kind=(ch[pre[y]][0]==y); if(ch[y][kind]==x){ Rotate(x,!kind); Rotate(x,kind); }else{ Rotate(y,kind); Rotate(x,kind); } } } if(goal==0)root=x; } void built(int &x,int L,int R,int fa) { if(L>R)return; int mid=(R+L)>>1; newnode(x,fa,mid); built(ch[x][0],L,mid-1,x); built(ch[x][1],mid+1,R,x); push_up(x); } void init(int n) { siz[0]=pre[0]=0; root=tot=ch[0][0]=ch[0][1]=0; newnode(root,0,inf); newnode(ch[root][1],root,inf); built(ch[ch[root][1]][0],1,n,ch[root][1]); push_up(ch[root][1]); push_up(root); } int Get_kth(int x,int k){ push_down(x); int sz=siz[ch[x][0]]+1; if(sz==k)return x; if(sz>k)return Get_kth(ch[x][0],k); return Get_kth(ch[x][1],k-sz); } void reverse(int L,int R) { Splay(Get_kth(root,L-1),0); Splay(Get_kth(root,R+1),root); upadte_rev(ch[ch[root][1]][0]); } void append_to_end() { int t=ch[ch[root][1]][0]; ch[ch[root][1]][0]=0; push_up(ch[root][1]); push_up(root); Splay(Get_kth(root,siz[root]-1),0); Splay(Get_kth(root,siz[root]),root); ch[ch[root][1]][0]=t; pre[t]=ch[root][1]; push_up(ch[root][1]); push_up(root); } void print(int x){ if(!x)return; push_down(x); print(ch[x][0]); if(key[x]!=inf)printf("%d\n",key[x]); print(ch[x][1]); } int main(int argc, char const *argv[]) { int n,m,L,R; while(~scanf("%d%d",&n,&m)) { init(n); while(m--){ scanf("%d%d",&L,&R); reverse(L+1,R+1); append_to_end(); } print(root); } return 0; }
标签:bst splay 二叉树 namespace 序列维护
原文地址:http://blog.csdn.net/acvcla/article/details/41662481