题目
题目描述
你将要实现一个功能强大的整数序列编辑器。
在开始时,序列是空的。
编辑器共有五种指令,如下:
1、“I x”,在光标处插入数值x。
2、“D”,将光标前面的第一个元素删除,如果前面没有元素,则忽略此操作。
3、“L”,将光标向左移动,跳过一个元素,如果左边没有元素,则忽略此操作。
4、“R”,将光标向右移动,跳过一个元素,如果右边没有元素,则忽略次操作。
5、“Q k”,假设此刻光标之前的序列为a1,a2,…,an,输出max(1≤i≤k)Si,其中Si=a1+a2+…+ai。
输入格式
第一行包含一个整数Q,表示指令的总数。
接下来Q行,每行一个指令,具体指令格式如题目描述。
输出格式
每一个“Q k”指令,输出一个整数作为结果,每个结果占一行。
样例
样例输入
8
I 2
I -1
I 1
Q 3
L
D
R
Q 2
样例输出
2
3
数据范围与提示
下图包含了对样例的过程描述:
思路
本题的特殊点在于,I,D,L,R四种操作都在光标位置处发生,并且操作完成后光标的变化不大(最多一个位置);
根据这种“始终在序列中间某个位置进行修改”的性质,不难想到一种“对顶栈”的做法
来看一组图
首先有两个空栈
假设两个栈里已经有了一些数
接着模拟各个操作
I x(插入x):
不妨设插入9吧
可以发现就是A.push(x);
D(删除光标前的一个数):
这时A中的9被删了
易得就是A.pop();
L(光标左移):
即为弹出A的栈顶,插入到B中
R(光标右移):
同上 滑稽
接下来就是最棘手的Q了
其实也不♂
因为查询操作的k不超过光标位置就是因为这个我和GM争了好久,所我们用一个数组f维护栈A的前缀和的最大值即可。设A的栈顶位置下标是pA,sum是序列A的前缀和的数组,每次遇到相关的操作就更新f、sum、pA,所以:
Q k(查询前缀和最大值):
输出f[k]即可
综上所述:
对于I x操作:
1.把x插入栈A(更新pA)
2.更新sum[pA]=sum[pA-1]+A[pA]
3.更新f[pA]=max(f[pA-1],sum[pA])
对于D操作
把A的栈顶弹出栈(更新pA)
对于L操作
弹出A的栈顶,插入到B中(更新pA)
对于R操作
1.弹出B的栈顶,插入到A中(更新pA)
2.更新sum[pA]=sum[pA-1]+A[pA]
3.更新f[pA]=max(f[pA-1],sum[pA])
对于Q k询问
直接返回f[k]