【模板】Splay
如题,这是一个模板。。。
1 #include <algorithm> 2 #include <iostream> 3 #include <cstring> 4 #include <cstdio> 5 #include <cctype> 6 7 inline void read(int & x) 8 { 9 x = 0; 10 int k = 1; 11 char c = getchar(); 12 while (!isdigit(c)) 13 if (c == '-') c = getchar(), k = -1; 14 else c = getchar(); 15 while (isdigit(c)) 16 x = (x << 1) + (x << 3) + (c ^ 48), 17 c = getchar(); 18 x *= k; 19 } 20 21 const int MAXN = 101010; 22 23 int rt = 0, tot = 0; 24 int faz[MAXN], siz[MAXN], cnt[MAXN], val[MAXN], son[MAXN][2]; 25 26 int Getson(int u) 27 { 28 return son[faz[u]][1] == u; 29 } 30 31 void Pushup(int u) 32 { 33 siz[u] = siz[son[u][0]] + siz[son[u][1]] + cnt[u]; 34 } 35 36 void Rotate(int u) 37 { 38 int y = faz[u], z = faz[y], ch = Getson(u); 39 int b = son[u][ch ^ 1], d = Getson(y); 40 son[u][ch ^ 1] = y, son[y][ch] = b; 41 faz[y] = u, faz[b] = y, faz[u] = z; 42 if (z) son[z][d] = u; 43 Pushup(y), Pushup(u); 44 } 45 46 void Splay(int u, int tar) 47 { 48 while (faz[u] != tar) 49 { 50 if (faz[faz[u]] != tar) 51 if (Getson(u) == Getson(faz[u])) Rotate(faz[u]); 52 else Rotate(u); 53 Rotate(u); 54 } 55 if (!tar) rt = u; 56 } 57 58 int Getmin(int u) 59 { 60 while (son[u][0]) u = son[u][0]; 61 return u; 62 } 63 64 int Getmax(int u) 65 { 66 while (son[u][1]) u = son[u][1]; 67 return u; 68 } 69 70 int Getx(int x) 71 { 72 int cur = rt, las = 0; 73 while (cur && val[cur] != x) 74 { 75 las = cur; 76 if (x < val[cur]) cur = son[cur][0]; 77 else cur = son[cur][1]; 78 } 79 return cur ? cur : las; 80 } 81 82 //void Insert(int x) 83 //{ 84 // int u = Getx(x); 85 // if (u && val[u] == x) 86 // { 87 // ++cnt[u]; 88 // ++siz[u]; 89 // Splay(u, 0); 90 // return; 91 // } 92 // val[++tot] = x; 93 // faz[tot] = u; 94 // cnt[tot] = siz[tot] = 1; 95 // if (u) son[u][x > val[u]] = tot; 96 // if (!rt) rt = tot; 97 // Splay(tot, 0); 98 //} 99 100 inline void Insert(int x) 101 { 102 int u = rt, las = 0; 103 while (u) 104 { 105 las = u; 106 if (x == val[u]) 107 { 108 ++siz[u]; 109 ++cnt[u]; 110 Splay(u, 0); 111 return; 112 } 113 if (x > val[u]) u = son[u][1]; 114 else u = son[u][0]; 115 } 116 u = ++tot; 117 val[u] = x; 118 faz[u] = las; 119 son[las][x > val[las]] = u; 120 siz[u] = cnt[u] = 1; 121 son[u][0] = son[u][1] = 0; 122 if (!rt) rt = u; 123 Splay(u, 0); 124 } 125 126 //void Delete(int x) 127 //{ 128 // int u = Getx(x); 129 // Splay(u, 0); 130 // if (cnt[u] > 1) { --cnt[u], --siz[u]; return; } 131 // if (!son[u][0] || !son[u][1]) { rt = son[u][0] | son[u][1]; faz[rt] = 0; return; } 132 // faz[son[u][0]] = 0; 133 // int bg = Getmax(son[u][0]); 134 // Splay(bg, 0); 135 // son[bg][1] = son[u][1]; 136 // faz[son[u][1]] = bg; 137 //} 138 139 inline void Delete(int x) 140 { 141 int u = rt; 142 while (u) 143 { 144 if (x == val[u]) 145 { 146 Splay(u, 0); 147 if (cnt[u] > 1) 148 { --cnt[u], --siz[u]; return; } 149 if (!son[u][0] || !son[u][1]) 150 { rt = son[u][0] | son[u][1]; faz[rt] = 0; return; } 151 faz[son[u][0]] = faz[son[u][1]] = 0; 152 int newrt = Getmin(son[u][1]); 153 faz[son[u][0]] = newrt; 154 son[newrt][0] = son[u][0]; 155 Splay(newrt, 0); 156 Pushup(newrt); 157 return; 158 } 159 else if (x > val[u]) u = son[u][1]; 160 else u = son[u][0]; 161 } 162 } 163 164 inline int GetKth(int k) 165 { 166 int u = rt; 167 while (u) 168 if (siz[son[u][0]] >= k) u = son[u][0]; 169 else if (siz[son[u][0]] + cnt[u] < k) k -= siz[son[u][0]] + cnt[u], u = son[u][1]; 170 else return val[u]; 171 } 172 173 int GetRank(int x) 174 { 175 int u = Getx(x); 176 Splay(u, 0); 177 return siz[son[u][0]] + 1; 178 } 179 180 int Pre(int x) 181 { 182 int u = Getx(x); 183 if (val[u] < x) return val[u]; 184 return val[Getmax(son[u][0])]; 185 } 186 187 int Suf(int x) 188 { 189 int u = Getx(x); 190 if (val[u] > x) return val[u]; 191 return val[Getmin(son[u][1])]; 192 } 193 194 int n, m, opt, x; 195 196 signed main() 197 { 198 read(m); 199 for (int i = 1; i <= m; ++i) 200 { 201 read(opt), read(x); 202 if (opt == 1) Insert(x); 203 if (opt == 2) Delete(x); 204 if (opt == 3) printf("%d\n", GetRank(x)); 205 if (opt == 4) printf("%d\n", GetKth(x)); 206 if (opt == 5) printf("%d\n", Pre(x)); 207 if (opt == 6) printf("%d\n", Suf(x)); 208 } 209 return 0; 210 }