如今请求你维护一个数列,要求提供如下两种操做:html
一、 查询操做。node
语法:Q L
ios
功能:查询当前数列中末尾L个数中的最大的数,并输出这个数的值。ui
限制:LL不超过当前数列的长度。(L > 0)(L>0)spa
二、 插入操做。code
语法:A n
orm
功能:将nn加上tt,其中tt是最近一次查询操做的答案(若是还未执行过查询操做,则t=0t=0),并将所得结果对一个固定的常数DD取模,将所得答案插入到数列的末尾。htm
限制:nn是整数(可能为负数)而且在长整范围内。blog
注意:初始时数列是空的,没有一个数。ip
第一行两个整数,MM和DD,其中MM表示操做的个数(M \le 200,000)(M≤200,000),DD如上文中所述,知足(0<D<2,000,000,000)(0<D<2,000,000,000)
接下来的MM行,每行一个字符串,描述一个具体的操做。语法如上文所述。
对于每个查询操做,你应该按照顺序依次输出结果,每一个结果占一行。
5 100 A 96 Q 1 A 97 Q 1 Q 2
96 93 96
[JSOI2008]
本题数据已增强
题解:为线段树基础……适合刚学线段树的人写一下开拓一下思路。根据题目咱们能够将线段的sum改成该线段中的最大值,这样会简单快速许多,具体见下代码;
#define _CRT_SECURE_NO_DepRECATE #define _CRT_SECURE_NO_WARNINGS #include <cstdio> #include <iostream> #include <cmath> #include <iomanip> #include <string> #include <algorithm> #include <bitset> #include <cstdlib> #include <cctype> #include <iterator> #include <vector> #include <cstring> #include <cassert> #include <map> #include <queue> #include <set> #include <stack> #define ll long long #define INF 0x3f3f3f3f #define ld long double const ld pi = acos(-1.0L), eps = 1e-8; int qx[4] = { 0,0,1,-1 }, qy[4] = { 1,-1,0,0 }, qxx[2] = { 1,-1 }, qyy[2] = { 1,-1 }; using namespace std; struct node { ll l = 0, r = 0, sum = 0, plz = 0, mlz = 1; }tree[1000000]; ll p = INF, maxx; inline void build(int i, int l, int r, int insert,int num)//树的编号 最左端 最右端 插入的值 插入的下标 { tree[i].l = l; tree[i].r = r; if (l == r)//找到该点即替换为insert { tree[i].sum = insert; } else { if ((l + r) / 2 >= num) { build(i << 1, l, (l + r) / 2, insert, num); } else { build(i << 1 | 1, (l + r) / 2 + 1, r, insert, num); } tree[i].sum = max(tree[i << 1].sum, tree[i << 1 | 1].sum);//每一个线段的sum为该线段的最大值 } } inline ll search_max(int i, int l, int r) { if (tree[i].l >= l && tree[i].r <= r)//因sum即表明该线段的最大值,因此找到彻底包含的线段就能够直接返回sum { return tree[i].sum; } if (tree[i].l > r || tree[i].r < l) { return 0; } ll ans = -INF; if (l <= tree[i << 1].r) { ans = max(ans, search_max(i << 1, l, r)); } if (r >= tree[i << 1 | 1].l) { ans = max(ans, search_max(i << 1 | 1, l, r)); } return ans; } int main() { ios::sync_with_stdio(false); cin.tie(0); ll m, d, t = 0, sum = 1, b,input; char x; cin >> m >> d; for (int i = 0; i < m; i++) { cin >> x; if (x == 'A') { cin >> input; input = (input + t) % d; build(1, 1, m, input, sum);//由于最多只能插入m个,因此能够直接以m为r sum++; } else { cin >> b; t = search_max(1, sum - b, sum - 1); cout << t << endl; } } return 0; }