题解:
长度定为3
线段树维护区间hash值
从左向右处理,依次在数轴上插入处理的元素;
如果当前数轴不对称,则缺失的那个元素一定在后面出现
#include<iostream>
#include<cstdio>
#include<cstring>
using namespace std;
typedef unsigned long long uLint;
const uLint bas=233;
const int maxn=100009;
int T;
int n;
uLint fac[maxn];
int a[maxn];
struct SegmentTree{
int l,r;
uLint hl,hr;
}tree[maxn<<2];
void pushup(int now){
tree[now].hl=tree[now<<1].hl*fac[tree[now<<1|1].r-tree[now<<1|1].l+1]+tree[now<<1|1].hl;
tree[now].hr=tree[now<<1|1].hr*fac[tree[now<<1].r-tree[now<<1].l+1]+tree[now<<1].hr;
}
void BuildTree(int now,int l,int r){
tree[now].l=l;tree[now].r=r;tree[now].hl=tree[now].hr=0;
if(l==r)return;
int mid=(l+r)>>1;
BuildTree(now<<1,l,mid);
BuildTree(now<<1|1,mid+1,r);
}
void Updatapoint(int now,int p){
if(tree[now].l==tree[now].r){
tree[now].hl=tree[now].hr=1;return;
}
int mid=(tree[now].l+tree[now].r)>>1;
if(p<=mid)Updatapoint(now<<1,p);
else Updatapoint(now<<1|1,p);
pushup(now);
}
uLint Queryhash(int now,int ll,int rr,int opty){
if(tree[now].l>=ll&&tree[now].r<=rr){
if(opty==0)return tree[now].hl;
else return tree[now].hr;
}
int mid=(tree[now].l+tree[now].r)>>1;
uLint ret=0;
if(opty==0){
if(ll<=mid&&rr>mid){
ret=Queryhash(now<<1,ll,rr,opty)*fac[min(rr-mid,tree[now].r-mid)]+Queryhash(now<<1|1,ll,rr,opty);
}else if(ll<=mid){
ret=Queryhash(now<<1,ll,rr,opty);
}else{
ret=Queryhash(now<<1|1,ll,rr,opty);
}
}else{
if(ll<=mid&&rr>mid){
ret=Queryhash(now<<1|1,ll,rr,opty)*fac[min(mid-tree[now].l,mid-ll)+1]+Queryhash(now<<1,ll,rr,opty);
}else if(ll<=mid){
ret=Queryhash(now<<1,ll,rr,opty);
}else{
ret=Queryhash(now<<1|1,ll,rr,opty);
}
}
return ret;
}
int main(){
scanf("%d",&T);
fac[0]=1;
for(int i=1;i<=10000;++i)fac[i]=fac[i-1]*233;
while(T--){
int fla=0;
scanf("%d",&n);
BuildTree(1,1,n);
for(int i=1;i<=n;++i){
int x;scanf("%d",&x);
Updatapoint(1,x);
int len=min(x,n-x+1);
uLint tmp1=Queryhash(1,x-len+1,x,0);
uLint tmp2=Queryhash(1,x,x+len-1,1);
if(tmp1!=tmp2)fla=1;
}
if(fla)printf("Y\n");
else printf("N\n");
}
return 0;
}