洛谷:P3391 【模板】文艺平衡树(Splay)
1 #include<cstdio>
2 #include<iostream>
3 #include<algorithm>
4 using namespace std;
5 const int MAXN=110000;
6 int n,m,tp,root,CNT;
7 int key[MAXN],lz[MAXN],fa[MAXN],sz[MAXN],val[MAXN],q[MAXN],Q[MAXN],ch[MAXN][2];
8 void update(int k){ sz[k]=sz[ch[k][0]]+sz[ch[k][1]]+1; }
9 void rotate(int x,int &y)
10 {
11 int old=fa[x],oldf=fa[old],op=ch[old][1]==x;
12 if(old==y) y=x;
13 else ch[oldf][ch[oldf][1]==old]=x;
14 fa[x]=oldf;
15 fa[ch[x][op^1]]=old; ch[old][op]=ch[x][op^1];
16 fa[old]=x; ch[x][op^1]=old;
17 update(old); update(x);
18 }
19 void down(int x)
20 {
21 if(lz[x])
22 {
23 lz[x]^=1; lz[ch[x][0]]^=1; lz[ch[x][1]]^=1;
24 swap(ch[x][0],ch[x][1]);
25 }
26 }
27 void splay(int x,int &y)
28 {
29 int now=x,old,oldf;Q[++tp]=now;
30 while(now!=y) Q[++tp]=fa[now] , now=fa[now];
31 while(tp--) down(Q[tp]);
32 while(x!=y)
33 {
34 old=fa[x],oldf=fa[old];
35 if(old!=y){
36 if((ch[old][0]==x)^(ch[oldf][0]==old)) rotate(x,y);
37 else rotate(old,y);
38 }
39 rotate(x,y);
40 }
41 }
42 void Build(int &k,int ll,int rr,int FA)
43 {
44 int mid=(ll+rr)/2;
45 k=++CNT; fa[k]=FA; key[k]=val[mid];
46 if(mid>ll) Build(ch[k][0],ll,mid-1,k);
47 if(mid<rr) Build(ch[k][1],mid+1,rr,k);
48 update(k);
49 }
50 int findx(int x)//注意下放。
51 {
52 int now=root;
53 while(1)
54 {
55 down(now);
56 if(x<=sz[ch[now][0]]) now=ch[now][0];
57 else
58 {
59 x-=sz[ch[now][0]]+1;
60 if(x==0) return now;
61 else now=ch[now][1];
62 }
63 }
64 }
65 void rev(int L,int R)
66 {
67 int ll=findx(L-1),rr=findx(R+1);
68 splay(ll,root);
69 splay(rr,ch[root][1]);
70 lz[ch[ch[root][1]][0]]^=1;
71 }
72 void dfs(int u)
73 {
74 down(u);
75 if(ch[u][0]) dfs(ch[u][0]);
76 if(key[u]!=0&&key[u]!=n+1) printf("%d ",key[u]);
77 if(ch[u][1]) dfs(ch[u][1]);
78 }
79 int main()
80 {
81 scanf("%d%d",&n,&m);
82 for(int i=1;i<=n;i++)val[i]=i;
83 Build(root,0,n+1,0);
84 for(int i=1,L,R;i<=m;i++)
85 {
86 scanf("%d%d",&L,&R);
87 L++; R++; rev(L,R);
88 }
89 dfs(root); puts("");
90 return 0;
91 }