传送门
题解:建主席树,然后由于这个题的性质:区间[l,r]内出现次数大于(r-l+1)/2的数一定只有一个,要么在[l,mid]中,要么在[mid+1,r]中,所以可以通过在主席树上二分查找得到。
如果换成大于(r-l+1)/3可能就要想别的办法了。。。
#include<bits/stdc++.h>
using namespace std;
#define lson lc[pre],lc[rt],l,mid
#define rson rc[pre],rc[rt],mid+1,r
const int MAXN=5e5+2;
int n,q;
int root[MAXN],lc[MAXN*20],rc[MAXN*20],sum[MAXN*20],tim=0;
inline int read() {
int x=0,f=1;char c=getchar();
while (c<'0'||c>'9') {if (c=='-') f=-1;c=getchar();}
while (c>='0'&&c<='9') x=x*10+c-'0',c=getchar();
return x*f;
}
void insert(int pre,int &rt,int l,int r,int val) {
rt=++tim;
sum[rt]=sum[pre]+1;
if (l==r) return ;
lc[rt]=lc[pre],rc[rt]=rc[pre];
int mid=(l+r)>>1;
if (val<=mid) insert(lson,val);
else insert(rson,val);
}
int query(int pre,int rt,int l,int r,int val) {
if (l==r) return sum[rt]-sum[pre]>val?l:0;
int mid=(l+r)>>1;
if (sum[lc[rt]]-sum[lc[pre]]>val) return query(lson,val);
else if (sum[rc[rt]]-sum[rc[pre]]>val) return query(rson,val);
else return 0;//critical!!!
}
int main() {
// freopen("bzoj 3524.in","r",stdin);
n=read(),q=read();
memset(sum,0,sizeof(sum));
memset(lc,0,sizeof(lc));
memset(rc,0,sizeof(rc));
root[0]=0;
for (register int i=1;i<=n;++i) insert(root[i-1],root[i],1,n,read());
for (register int i=0;i<q;++i) {
int L=read(),R=read();
printf("%d\n",query(root[L-1],root[R],1,n,(R-L+1)>>1));
}
return 0;
}