标签:using insert style swap targe seq names multi struct
1 #include<cstdio> 2 #include<cstring> 3 #include<cstdlib> 4 #include<cmath> 5 #include<iomanip> 6 #include<iostream> 7 #include<algorithm> 8 using namespace std; 9 const int N=3e5+7; 10 int n,m,root,tot; 11 int cnt,ans[N]; 12 struct Node{ 13 int ch[2],val,fa; 14 int size,mark; 15 void add(int x,int father){ 16 mark=ch[0]=ch[1]=0; 17 fa=father;val=x;size=1;} 18 }t[N]; 19 inline int read() 20 { 21 char ch=getchar();int num=0;bool flag=false; 22 while(ch<‘0‘||ch>‘9‘){if(ch==‘-‘)flag=true;ch=getchar();} 23 while(ch>=‘0‘&&ch<=‘9‘){num=num*10+ch-‘0‘;ch=getchar();} 24 return flag?-num:num; 25 } 26 inline void pushup(int x) 27 { 28 int l=t[x].ch[0],r=t[x].ch[1]; 29 t[x].size=t[l].size+t[r].size+1; 30 } 31 inline void pushdown(int x) 32 { 33 if(t[x].mark){ 34 t[t[x].ch[0]].mark^=1; 35 t[t[x].ch[1]].mark^=1; 36 swap(t[x].ch[0],t[x].ch[1]); 37 t[x].mark=0;} 38 } 39 inline void rotate(int x) 40 { 41 int y=t[x].fa; 42 int z=t[y].fa; 43 int k=(t[y].ch[1]==x); 44 t[z].ch[t[z].ch[1]==y]=x; 45 t[x].fa=z; 46 t[y].ch[k]=t[x].ch[k^1]; 47 t[t[x].ch[k^1]].fa=y; 48 t[x].ch[k^1]=y; 49 t[y].fa=x; 50 pushup(y);pushup(x); 51 } 52 inline void splay(int x,int tag) 53 { 54 while(t[x].fa!=tag){ 55 int y=t[x].fa; 56 int z=t[y].fa; 57 if(z!=tag) 58 (t[y].ch[1]==x)^(t[z].ch[1]==y)? 59 rotate(x):rotate(y); 60 rotate(x);} 61 if(tag==0)root=x; 62 } 63 inline void insert(int x) 64 { 65 int now=root,fa=0; 66 while(now) 67 fa=now,now=t[now].ch[x>t[now].val]; 68 now=++tot; 69 if(fa)t[fa].ch[x>t[fa].val]=now; 70 t[now].add(x,fa); 71 splay(now,0); 72 } 73 inline int find(int x) 74 { 75 int now=root; 76 while(555){ 77 pushdown(now); 78 if(t[t[now].ch[0]].size>=x)now=t[now].ch[0]; 79 else if(t[t[now].ch[0]].size+1==x)return now; 80 else x-=(t[t[now].ch[0]].size+1),now=t[now].ch[1]; 81 } 82 } 83 inline int getmax(int x) 84 { 85 pushdown(x); 86 while(t[x].ch[1]){ 87 x=t[x].ch[1]; 88 pushdown(x);} 89 return x; 90 } 91 inline void merge(int x,int y) 92 { 93 t[x].ch[1]=y; 94 t[y].fa=x; 95 } 96 inline void flip(int l,int r) 97 { 98 l=find(l),r=find(r+2); 99 splay(l,0);splay(r,l); 100 t[t[t[root].ch[1]].ch[0]].mark^=1; 101 } 102 inline void cut(int x,int y,int z) 103 { 104 int l=find(x),r=find(y+2); 105 splay(l,0);splay(r,l); 106 //找到移动区间的左右端点的位置并调整至根节点 107 int root1=t[t[root].ch[1]].ch[0]; 108 t[t[root].ch[1]].ch[0]=0; 109 //将该区间“截”下来 110 pushup(t[root].ch[1]); 111 pushup(root); 112 //调整节点信息 113 int neo=find(z+1); 114 splay(neo,0); 115 //找到放入区间的左端点并调整至根节点 116 int root2=t[root].ch[1]; 117 //记录下当前的右端点,因为待会儿合并时会将它直接去掉 118 merge(root,root1); 119 pushup(root); 120 //将截取区间接到当前根节点的右端点 121 int maxx=getmax(root); 122 splay(maxx,0); 123 //找到已经放入的区间的右端点并将其调整至根节点 124 merge(root,root2); 125 pushup(root); 126 //将之前被截取下来的端点和根节点 127 } 128 inline void travel(int now) 129 { 130 pushdown(now); 131 if(t[now].ch[0])travel(t[now].ch[0]); 132 if(t[now].val>1&&t[now].val<n+2) 133 ans[++cnt]=t[now].val-1; 134 if(t[now].ch[1])travel(t[now].ch[1]); 135 } 136 int main() 137 { 138 while(555){ 139 n=read();m=read(); 140 if(n<0||m<0)break; 141 root=tot=0; 142 for(int i=1;i<=n+2;i++) 143 insert(i); 144 char opt[5];int x,y,z; 145 for(int i=1;i<=m;i++){ 146 scanf("%s",opt); 147 if(opt[0]==‘F‘){ 148 x=read();y=read(); 149 flip(x,y);} 150 else{ 151 x=read();y=read();z=read(); 152 cut(x,y,z);} 153 } 154 cnt=0; 155 travel(root); 156 for(int i=1;i<n;i++) 157 printf("%d ",ans[i]); 158 printf("%d\n",ans[n]); 159 } 160 return 0;
HDU3487 Play With Chain [Splay]
标签:using insert style swap targe seq names multi struct
原文地址:https://www.cnblogs.com/cytus/p/8869689.html