hdu 3487 splay
切割的话就split再merge,区间修改就splay然后lazy标记。
1 #include <iostream> 2 #include <cstring> 3 #include <cstdio> 4 using namespace std; 5 6 const int N = 300000; 7 int ans[N]; 8 int n, m, cnt; 9 10 struct Node 11 { 12 Node * ch[2]; 13 int val; 14 int rank; 15 int sz; 16 int flip; 17 18 int cmp( int x ) const 19 { 20 if ( x == rank ) return -1; 21 return x < rank ? 0 : 1; 22 } 23 24 void maintain() 25 { 26 sz = rank = 1; 27 if ( ch[0] != NULL ) 28 { 29 sz += ch[0]->sz; 30 rank += ch[0]->sz; 31 } 32 if ( ch[1] != NULL ) 33 { 34 sz += ch[1]->sz; 35 } 36 } 37 38 void pushdown() 39 { 40 if ( flip ) 41 { 42 swap( ch[0], ch[1] ); 43 flip = 0; 44 if ( ch[0] != NULL ) ch[0]->flip ^= 1; 45 if ( ch[1] != NULL ) ch[1]->flip ^= 1; 46 } 47 } 48 }; 49 50 void visit( int val ) 51 { 52 if ( val == 0 || val == n + 1 ) return ; 53 ans[cnt++] = val; 54 } 55 56 void inorder( Node * o ) 57 { 58 if ( o == NULL ) return ; 59 o->pushdown(); 60 inorder( o->ch[0] ); 61 visit( o->val ); 62 inorder( o->ch[1] ); 63 } 64 65 void rotate( Node * & o, int d ) 66 { 67 Node * k = o->ch[d ^ 1]; 68 o->ch[d ^ 1] = k->ch[d]; 69 k->ch[d] = o; 70 o->maintain(); 71 k->maintain(); 72 o = k; 73 } 74 75 void splay( Node * & o, int k ) 76 { 77 o->pushdown(); 78 o->maintain(); 79 int d = o->cmp(k); 80 if ( d != -1 ) 81 { 82 if ( d == 1 ) k -= o->rank; 83 Node * p = o->ch[d]; 84 p->pushdown(); 85 p->maintain(); 86 int d2 = p->cmp(k); 87 if ( d2 != -1 ) 88 { 89 int k2 = ( d2 == 0 ? k : k - p->rank ); 90 splay( p->ch[d2], k2 ); 91 if ( d == d2 ) 92 { 93 rotate( o, d ^ 1 ); 94 } 95 else 96 { 97 rotate( o->ch[d], d ); 98 } 99 } 100 rotate( o, d ^ 1 ); 101 } 102 } 103 104 Node * build( int l, int r ) 105 { 106 if ( l > r ) return NULL; 107 Node * o = new Node(); 108 int mid = ( l + r ) >> 1; 109 o->sz = r - l + 1; 110 o->val = mid; 111 o->rank = mid - l + 1; 112 o->flip = 0; 113 o->ch[0] = build( l, mid - 1 ); 114 o->ch[1] = build( mid + 1, r ); 115 return o; 116 } 117 118 void split( Node * o, int k, Node * & left, Node * & right ) 119 { 120 splay( o, k ); 121 left = o; 122 right = o->ch[1]; 123 o->ch[1] = NULL; 124 left->maintain(); 125 } 126 127 Node * merge( Node * left, Node * right ) 128 { 129 splay( left, left->sz ); 130 left->ch[1] = right; 131 left->maintain(); 132 return left; 133 } 134 135 int main () 136 { 137 while ( scanf("%d%d", &n, &m) != EOF ) 138 { 139 if ( n == -1 && m == -1 ) break; 140 Node * root = build( 0, n + 1 ); 141 char cmd[11]; 142 int a, b, c; 143 while ( m-- ) 144 { 145 scanf("%s", cmd); 146 if ( cmd[0] == 'C' ) 147 { 148 scanf("%d%d%d", &a, &b, &c); 149 Node * left, * mid, * right, * o; 150 split( root, a, left, o ); 151 split( o, b - a + 1, mid, right ); 152 root = merge( left, right ); 153 split( root, c + 1, left, right ); 154 root = merge( merge( left, mid ), right ); 155 } 156 else 157 { 158 scanf("%d%d", &a, &b); 159 splay( root, a ); 160 splay( root->ch[1], b + 2 - a ); 161 Node * p = root->ch[1]->ch[0]; 162 p->flip ^= 1; 163 } 164 } 165 cnt = 0; 166 inorder(root); 167 for ( int i = 0; i < n; i++ ) 168 { 169 printf("%d", ans[i]); 170 if ( i != n - 1 ) putchar(' '); 171 else putchar('\n'); 172 } 173 } 174 return 0; 175 }