# bzoj 3223 文艺平衡树 splay 区间翻转

bzoj-3223

splay 区间翻转最简单的应用。

  1 #include<bits/stdc++.h>
2 using namespace std;
3 #define Fopen freopen("_in.txt","r",stdin); freopen("_out.txt","w",stdout);
4 #define LL long long
5 #define ULL unsigned LL
6 #define fi first
7 #define se second
8 #define pb push_back
9 #define lson l,m,rt<<1
10 #define rson m+1,r,rt<<1|1
11 #define max3(a,b,c) max(a,max(b,c))
12 #define min3(a,b,c) min(a,min(b,c))
13 typedef pair<int,int> pll;
14 const int inf = 0x3f3f3f3f;
15 const LL INF = 0x3f3f3f3f3f3f3f3f;
16 const LL mod =  (int)1e9+7;
17 const int N = 1e5 + 100;
18 int tot = 0, root;
19 int n, m;
20 struct Node{
21     int son[2], pre;
22     int val, sz, is_swap;
23     void init(int x){
24         val = x;   sz = 1;
25         is_swap = pre = son[0] = son[1] = 0;
26     }
27 }tr[N];
28 void Push_up(int x){
29     if(!x) return;
30     tr[x].sz = tr[tr[x].son[1]].sz + tr[tr[x].son[0]].sz + 1;
31 }
32 void Push_down(int x){
33     if(tr[x].is_swap){
34         tr[x].is_swap = 0;
35         int &l = tr[x].son[0], &r = tr[x].son[1];
36         tr[l].is_swap ^= 1; tr[r].is_swap ^= 1;
37         swap(l, r);
38     }
39 }
40 int build(int ll, int rr){
41     if(ll > rr) return 0;
42     int x = ++tot;
43     int m = ll + rr >> 1;
44     int &l = tr[x].son[0], &r = tr[x].son[1];
45     tr[x].init(m);
46     l = build(ll, m-1);
47     r = build(m+1, rr);
48     tr[l].pre = tr[r].pre = x;
49     Push_up(x);
50     return x;
51 }
52 void rotate(int x){
53     int y = tr[x].pre;
54     int z = tr[y].pre;
55     int k = x == tr[y].son[1];
56     tr[x].pre = z;
57     tr[z].son[y == tr[z].son[1]] = x;
58     tr[y].son[k] = tr[x].son[k^1];
59     tr[tr[y].son[k]].pre = y;
60     tr[x].son[k^1] = y;
61     tr[y].pre = x;
62     Push_up(y);
63 }
64 void splay(int x, int goal){
65     Push_down(x);
66     while(tr[x].pre != goal){
67         int y = tr[x].pre;
68         int z = tr[y].pre;
69         if(z != goal){
70             if((tr[y].son[0] == x) ^ (tr[z].son[0] == y))   rotate(x); ///x和y分别是y和z的同一段的儿子
71             else rotate(y);
72         }
73         rotate(x);
74     }
75     if(!goal) root = x;
76     Push_up(x);
77 }
78 void dfs(int x){
79     Push_down(x);
80     if(tr[x].son[0]) dfs(tr[x].son[0]);
81     if(tr[x].val <= n && tr[x].val >= 1)
82        printf("%d ", tr[x].val);
83     if(tr[x].son[1]) dfs(tr[x].son[1]);
84 }
85 int Find(int x, int p){
86     Push_down(p);
87     int &l = tr[p].son[0], &r = tr[p].son[1];
88     if(x == tr[l].sz + 1) return p;
89     if(x <= tr[l].sz) return Find(x, l);
90     return Find(x- tr[l].sz - 1, r);
91 }
92 int main(){
93     int l, r, pl, pr;
94     scanf("%d%d", &n, &m);
95     root = build(0, n+2);
96     while(m--){
97         scanf("%d%d", &l, &r);
98         pl = Find(l, root);
99         pr = Find(r+2, root);
100         splay(pl, 0);
101         splay(pr, root);
102         tr[tr[pr].son[0]].is_swap ^= 1;
103     }
104     dfs(root);
105     return 0;
106 }
View Code

posted @ 2018-07-30 08:53  Schenker  阅读(194)  评论(0编辑  收藏  举报