The stretching tree and the ranking tree are basically similar, directly on the template.
HYSBZ Maintenance Series
Linked list implementation
#include <cstdio> #include <cstring> #include <string> #include <algorithm> #include <cmath&
Gt #include <cstdlib> #include <utility> #include <map> #include <set> #include <queue> #
Include <vector> #include <iostream> #include <stack> using namespace std; #define INF 0x3f3f3f3f #define EPS 1e-6 #define CLR (A, V) memset (A, V, sizeof (a)) #define LL Long Long #define DBU G printf ("Here!!!
\ n ") #define REP (I, A, b) for (int i = (a); I < (b); i + +) #define PB push_back #define ULL unsigned long long #define PI ACOs ( -1.0) #define Lson L, M, RT << 1 #define Rson m+1, R, RT << 1 | 1 #define LOWBIT (x) ((x) & (-X) #define CASE int Test; scanf ("%d", &test); for (int cas = 1; CAs <= Test; cas + +) #define ALL (x) X.begin (), X.end () #define INS (x) x, X.begin () Typede
F pair < int, int > Pii;
typedef pair < Double, double > Pdd; typedef set < int > Set;
const int MAXN = 500005;
int Read_int () {int res = 0;
int ch; while (ch = getchar ()) &&!
(Ch >= ' 0 ' && ch <= ' 9 '))
{if (ch = =-1) return-1;
} while (Ch >= ' 0 ' && ch <= ' 9 ') {res = res*10+ (ch-' 0 ');
ch = getchar ();
} return res;
} struct Node {int x, CNT, LV, MV, RV, rev;
int MD, SUM;
struct Node * ch[2];
void maintain () {cnt = ch[0]->cnt+ch[1]->cnt+1;
sum = ch[0]->sum+ch[1]->sum+x;
Maintain substrings and LV = max (ch[0]->lv, Ch[0]->sum+x+max (0, CH[1]->LV));
RV = max (CH[1]->RV, Ch[1]->sum+x+max (0, CH[0]->RV));
MV = max (CH[0]->MV, CH[1]->MV);
MV = max (mv, Max (0, CH[0]->RV) +x+max (0, CH[1]->LV));
} void Modify (int s) {MD = s;
x = S; LV = MV = RV = Max (s, cnt*s);
s may be negative sum = cnt*s;
} void reverse () {swap (ch[0], ch[1]);
Swap (LV, RV); Rev ^= 1;
Note As long as the current Rev update} void Pushdown () {if (MD! = INF) {rev = 0;
if (CH[0]->CNT) ch[0]->modify (MD);
if (CH[1]->CNT) ch[1]->modify (MD);
md = INF;
} if (rev) {rev = 0;
if (ch[0]->cnt) ch[0]->reverse ();
if (ch[1]->cnt) ch[1]->reverse ();
}} int cmp (int k) {int d = k-ch[0]->cnt;
if (d = = 1) return-1; Return d <= 0?
0:1;
}}*root, *null;
int A[MAXN], CC;
Node * Build (int l, int r) {if (L >= R) return null;
int M = (l+r) >> 1;
Node * p = new node ();
p->x = P->LV = P->MV = P->RV = P->sum = A[m]; P->rev = 0;
P->MD = INF;
P->ch[0] = Build (L, M);
P->CH[1] = Build (m+1, R);
P->maintain ();
return p;
} void Rotate (node * &o, int k) {node * p = o->ch[k^1];
O->CH[K^1] = p->ch[k];
P->ch[k] = o;
O->maintain ();
P->maintain ();
o = p;
} void Splay (Node * &o, int k) {o->pushdown ();
int d = o->cmp (k);
if (d = = 1) K-= o->ch[0]->cnt+1;
if (d! =-1) {Node * p = o->ch[d];
P->pushdown ();
int D2 = p->cmp (k);
int K2 = (D2 = = 0? k:k-p->ch[0]->cnt-1);
if (D2! =-1) {splay (p->ch[d2], K2);
if (d = = D2) Rotate (o, d^1);
else Rotate (O->ch[d], D);
} Rotate (o, d^1);
} o->maintain (); } void Split (node * o, int k, node * &left, Node * &right) {splay ( O, k);
left = O;
right = o->ch[1];
LEFT->CH[1] = null;
Left->maintain ();
} node * Merge (node * left, node * right) {splay (left, left->cnt);
LEFT->CH[1] = right;
Left->maintain ();
return left;
} void Print (Node * o) {if (o = = null) return;
O->pushdown ();
Print (o->ch[0]);
printf ("%d", o->x);
Print (o->ch[1]);
void Remove (Node * &o) {if (o = = null) return;
Remove (o->ch[0]);
Remove (o->ch[1]);
Delete o;
o = null;
} void Solve () {int n, m, POS, tot, x;
Char op[15];
NULL = new Node ();
null->x = null->cnt = Null->rev = null->sum = 0;
NULL->LV = NULL->MV = NULL->RV =-inf;
Node *o, *left, *mid, *right;
Freopen ("In0.in", "R", stdin);
Freopen ("In1.out", "w", stdout);
scanf ("%d%d", &n, &m);
CC = 0;
for (int i = 1; I <= n; i + +) scanf ("%d", &a[i]);
root = Build (1, n+1);
while (M--) {scanf ("%s", op);
if (op[0] = = ' I ') {scanf ("%d%d", &pos, &tot);
if (tot = = 0) continue;
for (int i = 1; I <= tot; i + +) scanf ("%d", &a[i]);
o = Build (1, tot+1);
if (pos = = 0) root = Merge (o, root);
else {split (root, POS, left, right);
Root = Merge (merge (left, O), right);
}} else if (op[0] = = ' D ') {scanf ("%d%d", &pos, &tot);
if (tot = = 0) continue;
if (pos = = 1) {Split (root, Tot, left, O);
Remove (left);
root = O; } else {split (root, Pos-1, left, O);
Split (O, Tot, Mid, right);
Remove (mid);
Root = Merge (left, right);
}} else if (op[0] = = ' M ') {if (strcmp (OP, "make-same") = = 0) {
scanf ("%d%d%d", &pos, &tot, &x);
if (tot = = 0) continue;
if (pos = = 1) {Split (root, Tot, left, O);
Left->modify (x);
Root = Merge (left, O);
} else {split (root, Pos-1, left, O);
Split (O, Tot, Mid, right);
Mid->modify (x);
Root = Merge (merge (left, mid), right);
}} else printf ("%d\n", ROOT->MV);
} else if (op[0] = = ' R ') { scanf ("%d%d", &pos, &tot);
if (pos = = 1) {Split (root, Tot, left, O);
Left->reverse ();
Root = Merge (left, O);
} else {split (root, Pos-1, left, O);
Split (O, Tot, Mid, right);
Mid->reverse ();
Root = Merge (merge (left, mid), right);
}} else {scanf ("%d%d", &pos, &tot);
if (tot = = 0)//tot for 0 processing {printf ("0\n");
Continue;
} if (pos = = 1) {Split (root, Tot, left, O);
printf ("%d\n", left->sum);
Root = Merge (left, O);
} else {split (root, Pos-1, left, O);
Split (O, Tot, Mid, right); printf ("%d\n", mid->sum);
Root = Merge (merge (left, mid), right);
}}//print (root);
printf ("\ n");
}} int main () {solve ();
return 0;
}
Uvalive 3961 HDU 1890
This problem is mainly the operation of rotating a point to a node, so the parent node needs to be saved.
Array implementations
#include <cstdio> #include <cstring> #include <string> #include <algorithm> #include <cmath&
Gt #include <cstdlib> #include <utility> #include <map> #include <set> #include <queue> #
Include <vector> #include <iostream> #include <stack> using namespace std; #define INF 0x3f3f3f3f #define EPS 1e-6 #define CLR (A, V) memset (A, V, sizeof (a)) #define LL Long Long #define DBU G printf ("Here!!!
\ n ") #define REP (I, A, b) for (int i = (a); I < (b); i + +) #define PB push_back #define ULL unsigned long long #define PI ACOs ( -1.0) #define Lson L, M, RT << 1 #define Rson m+1, R, RT << 1 | 1 #define LOWBIT (x) ((x) & (-X) #define CASE int Test; scanf ("%d", &test); for (int cas = 1; CAs <= Test; cas + +) #define ALL (x) X.begin (), X.end () #define INS (x) x, X.begin () #defin
E key_value ch[ch[root][1]][0] typedef pair < int, int > Pii; typedef pair < Double, double > Pdd;
typedef set < int > set;
const int MAXN = 100005;
int Read_int () {int res = 0;
int ch; while (ch = getchar ()) &&!
(Ch >= ' 0 ' && ch <= ' 9 '))
{if (ch = =-1) return-1;
} while (Ch >= ' 0 ' && ch <= ' 9 ') {res = res*10+ (ch-' 0 ');
ch = getchar ();
} return res;
} int ch[maxn][2], CNT[MAXN], REV[MAXN], PRE[MAXN];
int tot, PP[MAXN], root, KEY[MAXN], MP[MAXN];
void NewNode (int &r, int fa, int k) {R = + + tot;
Pre[r] = FA;
Ch[r][0] = ch[r][1] = Rev[r] = 0;
Key[r] = k;
} void Pushup (int x) {Cnt[x] = cnt[ch[x][0]]+cnt[ch[x][1]]+1;} void Rever (int x) {if (x = = 0)
return;
Swap (ch[x][0], ch[x][1]);
REV[X] ^= 1;
} void Pushdown (int x) {if (rev[x]) {rever (ch[x][0]);
Rever (ch[x][1]);
Rev[x] = 0; }} void Build (int &x, int L, int R, inT FA) {if (L >= R) {x = 0;
return;
} int M = (l+r) >> 1;
NewNode (x, FA, pp[m]);
mp[Pp[m]] = x;
Build (Ch[x][0], L, M, x);
Build (Ch[x][1], m+1, R, x);
Pushup (x);
} Pii A[MAXN]; int CMP (PII x, Pii y) {return X.first < Y.first | | x.first = = Y.first && x.second < Y.second;} void
Init (int n) {root = tot = 0;
for (int i = 1; I <= n; i + +) {scanf ("%d", &a[i].first);
A[i].second = i;
} sort (a+1, a+1+n, CMP);
for (int i = 1; I <= n; i + +) pp[A[i].second] = i;
Ch[root][0] = ch[root][1] = Cnt[root] = Rev[root] = Pre[root] = 0;
NewNode (root, 0,-1);
NewNode (ch[root][1], root,-1);
Build (Key_value, 1, n+1, ch[root][1]);
Pushup (ch[root][1]);
Pushup (root);
} void Rotate (int x, int k) {int y = pre[x];
CH[Y][K^1] = ch[x][k];
if (Ch[x][k]) pre[ch[x][k]] = y; Ch[x][k] = y;
if (Pre[y]) ch[pre[y] [ch[pre[y]][1] = = y] = x;
PRE[X] = Pre[y];
Pre[y] = x;
Pushup (y);
Pushup (x);
} void Splay (int x, int goal) {pushdown (x);
while (pre[x]! = goal) {int y = pre[x];
Pushdown (y);
Pushdown (x);
if (pre[y] = = goal) Rotate (x, ch[y][0] = = x);
else {int z = pre[y];
Pushdown (z);
Pushdown (y);
Pushdown (x);
int d = ch[z][1] = = y, D2 = ch[y][1] = = x;
if (d = = D2) Rotate (x, d^1);
else Rotate (x, D);
Rotate (x, d^1);
}} pushup (x);
if (goal = = 0) root = x;
} int get_kth (int x, int k) {pushdown (x);//note need to update down otherwise the intermediate run will be problematic int d = cnt[ch[x][0]]+1;
if (d = = k) return x;
if (d > k) return get_kth (Ch[x][0], k); Return get_kth (ch[x][1], k-d);
} void Solve () {int n;
Freopen ("In0.in", "R", stdin);
while (~ scanf ("%d", &n), N) {Init (n);
for (int i = 1; I <= n; i + +) {splay (mp[i], root); printf (i = = 1?)
"%d": "%d", I+cnt[key_value]);
Rever (Key_value);
Splay (Get_kth (ch[root][1], cnt[key_value]+2), root);
Splay (get_kth (Key_value, Cnt[key_value]), ch[root][1]);
int x = ch[key_value][0];
if (x) pre[x] = ch[root][1];
Key_value = x;
Pushup (ch[root][1]);
Pushup (root);
} printf ("\ n");
}} int main () {solve ();
return 0;
}