[JSOI2008]最大数

题目
用两个栈,一个维护单调大小,一个维护编号;
询问就二分编号就好了

#include<bits/stdc++.h>
#define re return
#define ll long long
#define inc(i,l,r) for(int i=l;i<=r;++i)
#define dec(i,l,r) for(int i=l;i>=r;--i)
const int maxn=10e5+5;
using namespace std;
template<typename T>inline void rd(T&x)
{
	char c;bool f=0;
	while((c=getchar())<'0'||c>'9')if(c=='-')f=1;
	x=c^48;
	while((c=getchar())>='0'&&c<='9')x=x*10+(c^48);
	if(f)x=-x; 
}

ll n,d,t,m,st[2][maxn],top,cnt;
inline void add(int x)
{
	++cnt;
	while(top&&st[1][top]<=x)--top;
	st[1][++top]=x;
	st[0][top]=cnt;
}

inline void query(int x)
{
	int l=1,r=top;
	while(l<=r)
	{
		int mid=(l+r)>>1;
		if(st[0][mid]<x)l=mid+1;
		else r=mid-1;
	}
	
	printf("%d
",t=st[1][l]);
}
int main()
{
	rd(n);rd(d);
	char c;
	inc(i,1,n)
	{
		while((c=getchar())!='A'&&c!='Q');
		rd(m);
		if(c=='A')add((m+t)%d);
		else  query(cnt-m+1);
	} 
	re 0;
} 
原文地址:https://www.cnblogs.com/lsyyy/p/11261057.html