题意:给你一串序列,不断的将一个数 取出来放在最前面,不断的询问 rank位 和 数的rank,
解题思路:
1)线段树 + 树状数组(需要离散化)
2)Splay ,我把抽出来的建树,所以不是那么方便,可以离散化直接建树,这样会方便一点。
解题代码:
![](https://i-blog.csdnimg.cn/blog_migrate/8f900a89c6347c561fdf2122f13be562.gif)
![](https://i-blog.csdnimg.cn/blog_migrate/961ddebeb323a10fe0623af514929fc1.gif)
1 // File Name: hdu3436.pb_ds.cpp 2 // Author: darkdream 3 // Created Time: 2015年04月07日 星期二 14时26分13秒 4 5 #include<vector> 6 #include<list> 7 #include<map> 8 #include<set> 9 #include<deque> 10 #include<stack> 11 #include<bitset> 12 #include<algorithm> 13 #include<functional> 14 #include<numeric> 15 #include<utility> 16 #include<sstream> 17 #include<iostream> 18 #include<iomanip> 19 #include<cstdio> 20 #include<cmath> 21 #include<cstdlib> 22 #include<cstring> 23 #include<ctime> 24 #include<ext/pb_ds/tree_policy.hpp> 25 #include<ext/pb_ds/assoc_container.hpp> 26 #define maxn 100005 27 28 #define LL long long 29 30 using namespace __gnu_pbds; 31 using namespace std; 32 tree<int,int,greater<int>,rb_tree_tag,tree_order_statistics_node_update> mp; 33 int T; 34 int n , q; 35 char str[10]; 36 int tmp ; 37 struct SplayTree{ 38 int sz[maxn]; 39 int ch[maxn][2]; 40 int pre[maxn]; 41 int root ,top1,top2; 42 int ss[maxn],que[maxn]; 43 inline void Rotate(int x ,int f){ 44 int y = pre[x]; 45 push_down(y); 46 push_down(x); 47 ch[y][!f] = ch[x][f]; 48 pre[ ch[x][f] ] = y ; 49 pre[x] = pre[y]; 50 if(pre[x]) ch[pre[y]][ch[pre[y]][1] == y] = x; 51 ch[x][f] = y ; 52 pre[y] = x; 53 push_up(y); 54 } 55 inline void Splay(int x ,int goal){ 56 push_down(x); 57 while(pre[x] != goal){ 58 if(pre[ pre[x] ] == goal){ 59 Rotate(x,ch[pre[x]][0] == x); 60 } else { 61 int y = pre[x],z = pre[y]; 62 int f = (ch[z][0] == y); 63 if(ch[y][f] == x){ 64 Rotate(x,!f),Rotate(x,f); 65 } else{ 66 Rotate(y,f), Rotate(x,f); 67 } 68 } 69 } 70 push_up(x); 71 if(goal == 0 ) root = x; 72 } 73 inline void RotateTo(int k ,int goal){ 74 int x = root; 75 push_down(x); 76 while(sz[ch[x][0]] != k ){ 77 if(k < sz[ch[x][0]]){ 78 x = ch[x][0]; 79 }else{ 80 k -=(sz[ch[x][0]] + 1); 81 x = ch[x][1]; 82 } 83 push_down(x); 84 } 85 Splay(x,goal); 86 } 87 inline void NewNode(int &x ,int key,int val){ 88 if(top2) x = ss[--top2]; 89 else x = ++top1; 90 ch[x][0] = ch[x][1] = pre[x] = 0 ; 91 sz[x] = 1; 92 keys[x]= key; 93 vals[x] = val ; 94 } 95 inline void push_down(int x){ 96 97 } 98 inline void push_up(int x){ 99 sz[x] = 1 + sz[ch[x][1]] + sz[ch[x][0]]; 100 } 101 inline void init(){ 102 ch[0][0] = ch[0][1] = pre[0] = sz[0] = 0 ; 103 root = top1 = 0 ; 104 NewNode(root,0,0); 105 NewNode(ch[root][1],1e9,0); 106 sz[root] = 2; 107 pre[ch[root][1]] = root; 108 109 } 110 inline pair<int,int> find(int key) 111 { 112 int x = root ; 113 int k = 0 ; 114 for(;;) 115 { 116 if(key == keys[x]) 117 { 118 pair<int,int> ans = make_pair(vals[x],k+sz[ch[x][0]]); 119 Splay(x,0); 120 return ans; 121 } 122 bool f = (key > keys[x]); 123 if(ch[x][f] == 0 ) 124 { 125 pair<int,int> ans = make_pair(-1,k + sz[ch[x][0]] - (!f)); 126 Splay(x,0); 127 return ans ; 128 129 }else{ 130 if(f) 131 k += (sz[ch[x][0]] + 1); 132 x = ch[x][f]; 133 } 134 } 135 } 136 inline void insert(int key,int val){ 137 int x = root; 138 int k = 0 ; 139 for(;;) 140 { 141 if(key == keys[x]) 142 { 143 mp.erase(mp.find(vals[x])); 144 vals[x] = val; 145 Splay(x,0); 146 return; 147 } 148 int f = (key > keys[x]); 149 if(ch[x][f] == 0 ) 150 { 151 NewNode(ch[x][f],key,val); 152 pre[ch[x][f]] = x; 153 Splay(ch[x][f],0); 154 return; 155 }else{ 156 x = ch[x][f]; 157 } 158 } 159 } 160 inline int findrank(int site){ 161 int x = root ; 162 int k = 0 ; 163 int szmp= mp.size(); 164 int ans = site; 165 int p = root; 166 for(; x!= 0 ;) 167 { 168 int tmp = szmp + keys[x] - (k + sz[ch[x][0]]) + 1; 169 if(tmp > site) 170 { 171 x = ch[x][0]; 172 }else{ 173 ans = keys[x] + (site - (tmp) + 1) ; 174 p = x; 175 k += (sz[ch[x][0]] + 1); 176 x = ch[x][1]; 177 } 178 } 179 Splay(p,0); 180 return ans; 181 } 182 int vals[maxn]; 183 int keys[maxn]; 184 185 }spt; 186 int main(){ 187 scanf("%d",&T); 188 for(int CA = 1; CA <= T ; CA++) 189 { 190 mp.clear(); 191 spt.init(); 192 printf("Case %d:\n",CA); 193 scanf("%d %d",&n,&q); 194 for(int i= 1;i <= q;i ++) 195 { 196 scanf("%s %d",str,&tmp); 197 if(str[0] == 'T'){ 198 spt.insert(tmp,i); 199 mp[i] = tmp ; 200 }else if(str[0] == 'Q'){ 201 pair<int ,int > tt = spt.find(tmp); 202 if(tt.first != -1 ) 203 printf("%ld\n",mp.order_of_key(tt.first) + 1); 204 else{ 205 printf("%ld\n",mp.size()-tt.second + tmp); 206 } 207 }else{ 208 if(tmp <= mp.size()){ 209 printf("%d\n",mp.find_by_order(tmp-1)->second); 210 }else{ 211 printf("%d\n",spt.findrank(tmp)); 212 } 213 } 214 } 215 } 216 return 0; 217 }