1、题意:各种splay操作,一道好的模板题2333
2、分析:splay模板题,没啥解释QAQ
#include <stack> #include <cstdio> #include <cstdlib> #include <cstring> #include <algorithm> using namespace std; #define M 2000010 inline int read(){ char ch = getchar(); int x = 0, f = 1; while(ch < '0' || ch > '9'){ if(ch == '-') f = -1; ch = getchar(); } while('0' <= ch && ch <= '9'){ x = x * 10 + ch - '0'; ch = getchar(); } return x * f; } namespace splay{ struct Node{ Node *ch[2], *fa; char c; bool rev; int size; inline int which(); inline void reverse(){ rev ^= 1; swap(ch[0], ch[1]); } inline void pd(){ if(rev){ ch[0] -> reverse(); ch[1] -> reverse(); rev = false; } } inline void maintain(){ size = 1 + ch[0] -> size + ch[1] -> size; } Node(); } *null = new Node, ft[M]; int tot; Node::Node(){ size = 1; c = '\0'; ch[0] = ch[1] = fa = null; rev = false; } inline int Node::which(){ if(fa == null) return -1; return this == fa -> ch[1]; } inline void rotate(Node *o){ Node *p = o -> fa; int l = o -> which(), r = l ^ 1; o -> fa = p -> fa; if(p -> which() != -1) p -> fa -> ch[p -> which()] = o; p -> ch[l] = o -> ch[r]; if(o -> ch[r]) o -> ch[r] -> fa = p; o -> ch[r] = p; p -> fa = o; o -> ch[r] -> maintain(); o -> maintain(); } inline void splay(Node *o){ static stack<Node*> st; if(!o) return; Node *p = o; while(1){ st.push(p); if(p -> which() == -1) break; p = p -> fa; } while(!st.empty()){ st.top() -> pd(); st.pop(); } while(o -> which() != -1){ p = o -> fa; if(p -> which() != -1){ if(p -> which() ^ o -> which()) rotate(o); else rotate(p); } rotate(o); } } inline Node* Kth(Node *o, int k){ o -> pd(); int t = o -> ch[0] -> size + 1; if(k == t) return o; if(k < t) return Kth(o -> ch[0], k); return Kth(o -> ch[1], k - t); } inline Node *merge(Node *a, Node *b){ if(a == null) return b; if(b == null) return a; Node *p = Kth(a, a -> size); splay(p); Node *c = p; c -> ch[1] = b; b -> fa = c; c -> maintain(); return c; } inline void split(Node *o, int k, Node* &a, Node* &b){ if(k == 0){ a = null; b = o; return; } if(k == o -> size){ a = o; b = null; return; } Node *p = Kth(o, k); splay(p); o = p; o -> maintain(); b = p -> ch[1]; b -> fa = null; p -> ch[1] = null; a = p; a -> maintain(); } } using namespace splay; int main(){ null -> ch[0] = null -> ch[1] = null -> fa = null; null -> c = '\0'; null -> rev = false; null -> size = 0; int n = read(); int now = 0; Node *root = null; char str[10]; for(int i = 1; i <= n; i ++){ scanf("%s", str); if(str[0] == 'M'){ int x = read(); now = x; } else if(str[0] == 'I'){ int x = read(); Node *a, *b, *d = null; split(root, now, a, b); for(int i = 1; i <= x; i ++){ char ch = getchar(); Node *c = &ft[++ tot]; c -> c = ch; d = merge(d, c); } root = merge(a, d); root = merge(root, b); } else if(str[0] == 'D'){ int x = read(); Node *a, *b, *c; split(root, now, a, b); split(b, x, b, c); root = merge(a, c); } else if(str[0] == 'R'){ int x = read(); Node *a, *b, *c; split(root, now, a, b); split(b, x, b, c); b -> reverse(); root = merge(a, b); root = merge(root, c); } else if(str[0] == 'G'){ Node *p = Kth(root, now + 1); printf("%c\n", p -> c); } else if(str[0] == 'P'){ now --; } else{ now ++; } } return 0; }