1 #include<cstdio>
  2 #include<cstring>
  3 #include<algorithm>
  4 #define oo 0x7FFFFFFF
  5 #define MAXN 1000010
  6 using namespace std;
  7 struct SplayTree {
  8     int root, size;
  9     int a[MAXN], st[MAXN], top;
 10     int next[MAXN][2], pre[MAXN], key[MAXN], num[MAXN];
 11     bool flip[MAXN];
 12     int same[MAXN], sum[MAXN], MaxL[MAXN], MaxR[MAXN], MaxM[MAXN];
 13     inline void PushUp(int x) {
 14         int L, R;
 15         L = next[x][0];
 16         R = next[x][1];
 17         num[x] = num[L] + num[R] + 1;
 18         sum[x] = sum[L] + sum[R] + key[x];
 19         MaxL[x] = max(MaxL[L], sum[L] + key[x] + max(MaxL[R], 0));
 20         MaxR[x] = max(MaxR[R], sum[R] + key[x] + max(MaxR[L], 0));
 21         MaxM[x] = max(MaxM[L], MaxM[R]);
 22         MaxM[x] = max(MaxM[x], max(MaxR[L], 0) + key[x] + max(MaxL[R], 0));
 23     }
 24     inline void PushDown(int x) {
 25         int L, R;
 26         L = next[x][0];
 27         R = next[x][1];
 28         if (flip[x]) {
 29             flip[x] = false;
 30             swap(next[x][0], next[x][1]);
 31             if (L) {
 32                 flip[L] ^= true;
 33                 swap(MaxL[L], MaxR[L]);
 34             }
 35             if (R) {
 36                 flip[R] ^= true;
 37                 swap(MaxL[R], MaxR[R]);
 38             }
 39         }
 40         if (same[x] != -oo) {
 41             if (L) {
 42                 same[L] = key[L] = same[x];
 43                 sum[L] = num[L] * same[x];
 44                 MaxL[L] = MaxR[L] = MaxM[L] = max(same[x], sum[L]);
 45             }
 46             if (R) {
 47                 same[R] = key[R] = same[x];
 48                 sum[R] = num[R] * same[x];
 49                 MaxL[R] = MaxR[R] = MaxM[R] = max(same[x], sum[R]);
 50             }
 51             same[x] = -oo;
 52         }
 53     }
 54     void NewNode(int &x, int father, int val) {
 55         if (top != -1)
 56             x = st[top--];
 57         else
 58             x = ++size;
 59         flip[x] = false;
 60         next[x][0] = next[x][1] = 0;
 61         pre[x] = father;
 62         key[x] = sum[x] = MaxL[x] = MaxR[x] = MaxM[x] = val;
 63         num[x] = 1;
 64         same[x] = -oo;
 65     }
 66     void Build(int &x, int L, int R, int father) {
 67         if (L <= R) {
 68             int mid = (L + R) >> 1;
 69             NewNode(x, father, a[mid]);
 70             Build(next[x][0], L, mid - 1, x);
 71             Build(next[x][1], mid + 1, R, x);
 72             PushUp(x);
 73         }
 74     }
 75     void Init(int n) {
 76         top = -1;
 77         root = size = 0;
 78         next[0][0] = next[0][1] = pre[0] = key[0] = num[0] = sum[0] = 0;
 79         flip[0] = false;
 80         same[0] = MaxL[0] = MaxR[0] = MaxM[0] = -oo;
 81         NewNode(root, 0, -oo);
 82         NewNode(next[root][1], root, -oo);
 83         Build(next[next[root][1]][0], 1, n, next[root][1]);
 84         PushUp(next[root][1]);
 85         PushUp(root);
 86     }
 87     void Rotate(int x, int kind) {
 88         int y, z;
 89         y = pre[x];
 90         z = pre[y];
 91         PushDown(y);
 92         next[y][!kind] = next[x][kind];
 93         pre[next[x][kind]] = y;
 94         next[z][next[z][1] == y] = x;
 95         pre[x] = z;
 96         next[x][kind] = y;
 97         pre[y] = x;
 98         PushUp(y);
 99     }
100     void Splay(int x, int goal) {
101         if (x != goal) {
102             PushDown(x);
103             while (pre[x] != goal) {
104                 if (next[pre[x]][0] == x)
105                     Rotate(x, 1);
106                 else
107                     Rotate(x, 0);
108             }
109             PushUp(x);
110             if (!goal)
111                 root = x;
112         }
113     }
114     int Select(int k) {
115         int x;
116         PushDown(root);
117         for (x = root; num[next[x][0]] + 1 != k;) {
118             if (num[next[x][0]] + 1 > k)
119                 x = next[x][0];
120             else {
121                 k -= num[next[x][0]] + 1;
122                 x = next[x][1];
123             }
124             PushDown(x);
125         }
126         return x;
127     }
128     int GetSum(int x, int y) {
129         x = Select(x - 1);
130         y = Select(y + 1);
131         Splay(x, 0);
132         Splay(y, x);
133         return sum[next[y][0]];
134     }
135     void Recycle(int x) {
136         if (x) {
137             st[++top] = x;
138             Recycle(next[x][0]);
139             Recycle(next[x][1]);
140         }
141     }
142     void Delete(int x, int y) {
143         x = Select(x - 1);
144         y = Select(y + 1);
145         Splay(x, 0);
146         Splay(y, x);
147         Recycle(next[y][0]);
148         next[y][0] = 0;
149         PushUp(y);
150         PushUp(x);
151     }
152     void Flip(int x, int y) {
153         x = Select(x - 1);
154         y = Select(y + 1);
155         Splay(x, 0);
156         Splay(y, x);
157         y = next[y][0];
158         flip[y] ^= true;
159         swap(MaxL[y], MaxR[y]);
160     }
161     void MakeSame(int x, int y, int val) {
162         int t;
163         x = Select(x - 1);
164         y = Select(y + 1);
165         Splay(x, 0);
166         Splay(y, x);
167         t = next[y][0];
168         same[t] = key[t] = val;
169         sum[t] = val * num[t];
170         MaxL[t] = MaxR[t] = MaxM[t] = max(val, sum[t]);
171         PushUp(y);
172         PushUp(x);
173     }
174     int GetMin(int x) {
175         PushDown(x);
176         while (next[x][0]) {
177             x = next[x][0];
178             PushDown(x);
179         }
180         return x;
181     }
182     void Insert(int x, int cnt) {
183         int y;
184         x = Select(x);
185         Splay(x, 0);
186         y = GetMin(next[x][1]);
187         Splay(y, x);
188         Build(next[y][0], 1, cnt, y);
189         PushUp(y);
190         PushUp(x);
191     }
192     int MaxSum(int x, int y) {
193         x = Select(x - 1);
194         y = Select(y + 1);
195         Splay(x, 0);
196         Splay(y, x);
197         return MaxM[next[y][0]];
198     }
199 } spt;
200 int main() {
201     int n, q;
202     int pos, cnt, i, val;
203     char cmd[18];
204     while (~scanf("%d%d", &n, &q)) {
205         for (i = 1; i <= n; i++)
206             scanf("%d", &spt.a[i]);
207         spt.Init(n);
208         while (q--) {
209             scanf(" %s", cmd);
210             if (strcmp(cmd, "GET-SUM") == 0) {
211                 scanf("%d%d", &pos, &cnt);
212                 printf("%d\n", spt.GetSum(pos + 1, pos + cnt));
213             } else if (strcmp(cmd, "MAX-SUM") == 0)
214                 printf("%d\n", spt.MaxSum(2, spt.num[spt.root] - 1));
215             else if (strcmp(cmd, "INSERT") == 0) {
216                 scanf("%d%d", &pos, &cnt);
217                 for (i = 1; i <= cnt; i++)
218                     scanf("%d", &spt.a[i]);
219                 spt.Insert(pos + 1, cnt);
220             } else if (strcmp(cmd, "DELETE") == 0) {
221                 scanf("%d%d", &pos, &cnt);
222                 spt.Delete(pos + 1, pos + cnt);
223             } else if (strcmp(cmd, "MAKE-SAME") == 0) {
224                 scanf("%d%d%d", &pos, &cnt, &val);
225                 spt.MakeSame(pos + 1, pos + cnt, val);
226             } else if (strcmp(cmd, "REVERSE") == 0) {
227                 scanf("%d%d", &pos, &cnt);
228                 spt.Flip(pos + 1, pos + cnt);
229             }
230         }
231     }
232     return 0;
233 }
posted on 2012-08-15 20:46  DrunBee  阅读(777)  评论(0编辑  收藏  举报