QAQ
鹅鹅鹅饿鹅鹅鹅
虽说这个题啊,可以用线段树做,可是老师说不太好23333。
单调栈的作法,维护一个单调递减的栈(因为要找的是最大值啊,后面的比前面的大了前面的就没意义了不是么)
#include <cstdio>
#include <iostream>
using namespace std;
int p;
int a[999999],b[9999999];//a代表编号所代表的数,b为栈,其实是编号,编号所指向的数是单调的,为了便于查找。
int find(int x,int y,int k)
{
int m=(x+y)>>1;
while(x!=y)
{
if (b[m]<k) x=m+1;
if (b[m]==k) return m;
if (b[m]>k) y=m;
m=(x+y)>>1;
}
return m;
}
int main()
{
int n;
scanf("%d%d",&n,&p);
int cnt=0;
int sum=0;
int num=0;
for(int i=1;i<=n;i++)
{
int x;
char c[3];
scanf("%s%d",c,&x);
if(c[0]=='A')
{
x=(x+sum)%p;//之前查询的数与输入的数和modp
a[++cnt]=x;//数的编号++,值为x
while(num>0&&a[b[num]]<=x) num--;//当这个元素比栈顶元素大的时候栈顶出栈
b[++num]=cnt;//元素入栈
}
else
{
sum=a[b[find(1,num,cnt-x+1)]];//二分查找
printf("%d\n",sum);
}
}
return 0;
}