题目大意:要选一段最长的字符串,使得三种字符出现次数各不相同或只有一种
只有一种的直接就能扫出来,然后就想各不相同的
首先维护一个前缀和,代表到每个点时,前缀B,C,S的个数
然后令xi=bi-ci,yi=ci-si,zi=si-bi,每个点权值为自己的位置
如果两个点的xi,yi,zi均不相同,这一段就可以选
所以可以先按x排序,这样就干掉一维
然后我们设x相同的为一组,首先我们把包含权值为1的那一组提到最前面,包含权值为n的那组提到第二组的位置
然后维护6个树状数组
前三个维护最小值,分别代表y值与位置为1的y值相同而z值不同的最小值,以及z相同y不相同的,yz都不相同的
查询的时候,如果他的yz都跟位置为1的不相同,那最小值直接就是1
否则根据他的yz来决定去哪组查询最小值
后三个与这个同理,维护最大值
然后具体方式就是,对于每一组,先把这一组的都查询完,然后再插入
这时列一个表格可以发现,还是有一种情况没考虑到,就是最大值在第一组而最小值在第二组的情况,特殊处理一下就好了
神烦的代码,6800B+,除了树状数组基本啥也没有.....
61000msAC,吓尿我,估计如果我TLE了就不调了...正解1000B我也不知道是怎么做的
#include<iostream> #include<cstdio> #include<algorithm> #include<cstring> #define N 1000010 using namespace std; char s[N]; int n; struct ppp{int x,y,z,num;}a[N],a1[N],a2[N]; int cnt1,cnt2; bool cmp1(ppp x,ppp y){return x.x<y.x;} struct BIT { int c[N<<1]; void changemx(int x,int v) { for(;x<=n+N;x+=x&-x) c[x]=max(c[x],v); } void changemn(int x,int v) { // cout<<x-N<<'!'<<v<<endl; for(;x<=n+N;x+=x&-x) c[x]=min(c[x],v); } int checkmx(int x) { int ans=0; for(;x;x-=x&-x) ans=max(c[x],ans); return ans; } int checkmn(int x) { // cout<<x-N<<'?'; int ans=707185547; for(;x;x-=x&-x) ans=min(ans,c[x]); // cout<<ans<<endl; return ans; } }; BIT zy,zz,ny,nz; int main() { int i,j,k; scanf("%d",&n); scanf("%s",s+1); // //cout<<s+1;return 0; for(i=1;i<=n;i++) { a[i]=a[i-1]; a[i].num=i; if(s[i]=='B') a[i].x++; else if(s[i]=='C') a[i].y++; else a[i].z++; } int o,p,q,oo,pp,qq; for(i=1;i<=n;i++) { o=a[i].x;p=a[i].y;q=a[i].z; a[i].x=o-p;a[i].y=p-q;a[i].z=q-o; // cout<<a[i].x<<' '<<a[i].y<<' '<<a[i].z<<endl; } n++;a[n].x=0;a[n].y=0;a[n].z=0;a[n].num=0; int ans=0; o=a[n].x;p=a[n].y;q=a[n].z; oo=a[n-1].x;pp=a[n-1].y;qq=a[n-1].z; //cout<<n; sort(a+1,a+n+1,cmp1); int s1,t1,s2,t2; { i=1; while(a[i].x!=o) i++; j=i; while(a[j+1].x==a[i].x&&j<n) j++; s1=i;t1=j; for(k=i;k<=j;k++) cnt1++,a1[cnt1]=a[k]; i=1; while(a[i].x!=oo) i++; j=i; while(a[j+1].x==a[i].x&&j<n) j++; s2=i;t2=j; for(k=i;k<=j;k++) cnt2++,a2[cnt2]=a[k]; // cout<<s1<<' '<<t1<<' '<<s2<<' '<<t2<<endl; if(s1!=s2) { int e=max(t1,t2);j=e; for(i=e;i>cnt1+cnt2;i--) { while((j>=s1&&j<=t1)||(j>=s2&&j<=t2)) j--; // cout<<j; a[i]=a[j];j--; } for(i=1;i<=cnt1;i++) a[i]=a1[i]; for(i=1;i<=cnt2;i++) a[i+cnt1]=a2[i]; { /*puts(""); for(k=1;k<=n;k++) cout<<a[k].x<<' '<<a[k].y<<' '<<a[k].z<<' '<<a[k].num<<endl;*/ int maxn=-1,p3,qqq; for(k=1;k<=cnt1;k++) { if(a[k].num>maxn) maxn=a[k].num,p3=a[k].y,qqq=a[k].z; } // cout<<maxn; for(k=1;k<=cnt1;k++) { if(a[k].y!=p3) { zy.changemx(a[k].z+N,a[k].num); ny.changemx(N+1-a[k].z,a[k].num); } if(a[k].z!=qqq) { zz.changemx(a[k].y+N,a[k].num); nz.changemx(N+1-a[k].y,a[k].num); } } //cout<<' '<<p3<<' '<<qqq<<endl; for(k=cnt1+1;k<=cnt2+cnt1;k++) { if(a[k].y==p3) { ans=max(ans,zy.checkmx(a[k].z+N-1)-a[k].num+1); ans=max(ans,ny.checkmx(N-a[k].z)-a[k].num+1); if(a[k].z==qqq) { ans=max(ans,zz.checkmx(a[k].y+N-1)-a[k].num+1); ans=max(ans,nz.checkmx(N-a[k].y)-a[k].num+1); } } else { if(a[k].z==qqq) { // cout<<ans<<'!'; ans=max(ans,zz.checkmx(a[k].y+N-1)-a[k].num+1); ans=max(ans,nz.checkmx(N-a[k].y)-a[k].num+1); // cout<<ans<<endl; } else ans=max(ans,maxn-a[k].num+1); } //cout<<ans; } } } else { int e=t1;j=e; for(i=e;i>cnt1;i--) { while(j>=s1&&j<=t1) j--; a[i]=a[j];j--; } for(i=1;i<=cnt1;i++) a[i]=a1[i]; } } memset(zy.c,0,sizeof(zy.c)); memset(zz.c,0,sizeof(zz.c)); memset(ny.c,0,sizeof(ny.c)); memset(nz.c,0,sizeof(nz.c)); i=1; while(a[i].x!=oo) i++; j=i; while(a[j+1].x==a[i].x&&j<n) j++; for(k=i;k<=j;k++) { // //cout<<k<<' '; if(a[k].y!=pp) { //cout<<k<<a[k].z; zy.changemx(a[k].z+N,a[k].num); ny.changemx(N+1-a[k].z,a[k].num); } if(a[k].z!=qq) { zz.changemx(a[k].y+N,a[k].num); nz.changemx(N+1-a[k].y,a[k].num); } } i=1; while(i<=n) { j=i; while(a[j+1].x==a[i].x&&j<n) j++; if(a[i].x==oo){i=j+1;continue;} for(k=i;k<=j;k++) { if(a[k].y==pp) { ans=max(ans,zy.checkmx(a[k].z+N-1)-a[k].num+1); ans=max(ans,ny.checkmx(N-a[k].z)-a[k].num+1); if(a[k].z==qq) { ans=max(ans,zz.checkmx(a[k].y+N-1)-a[k].num+1); ans=max(ans,nz.checkmx(N-a[k].y)-a[k].num+1); } } else { if(a[k].z==qq) { ans=max(ans,zz.checkmx(a[k].y+N-1)-a[k].num+1); ans=max(ans,nz.checkmx(N-a[k].y)-a[k].num+1); } else ans=max(ans,n-a[k].num); } } for(k=i;k<=j;k++) { if(a[k].y!=pp) { // //cout<<k<<a[k].z; zy.changemx(a[k].z+N,a[k].num); ny.changemx(N+1-a[k].z,a[k].num); } if(a[k].z!=qq) { zz.changemx(a[k].y+N,a[k].num); nz.changemx(N+1-a[k].y,a[k].num); } } i=j+1; } //cout<<endl; memset(zy.c,0x3f,sizeof(zy.c)); memset(zz.c,0x3f,sizeof(zz.c)); memset(ny.c,0x3f,sizeof(ny.c)); memset(nz.c,0x3f,sizeof(nz.c)); i=1; while(a[i].x!=o) i++; j=i; while(a[j+1].x==a[i].x) j++; for(k=i;k<=j;k++) { if(a[k].y!=p) { zy.changemn(a[k].z+N,a[k].num); ny.changemn(N+1-a[k].z,a[k].num); } if(a[k].z!=q) { zz.changemn(a[k].y+N,a[k].num); nz.changemn(N+1-a[k].y,a[k].num); } } i=1; while(i<=n) { j=i; while(a[j+1].x==a[i].x&&j<n) j++; if(a[i].x==o){i=j+1;continue;} for(k=i;k<=j;k++) { if(a[k].y==p) { ans=max(ans,a[k].num-zy.checkmn(a[k].z+N-1)+1); ans=max(ans,a[k].num-ny.checkmn(N-a[k].z)+1); if(a[k].z==q) { ans=max(ans,a[k].num-zz.checkmn(a[k].y+N-1)+1); ans=max(ans,a[k].num-nz.checkmn(N-a[k].y)+1); } } else { if(a[k].z==q) { ans=max(ans,a[k].num-zz.checkmn(a[k].y+N-1)+1); ans=max(ans,a[k].num-nz.checkmn(N-a[k].y)+1); } else ans=max(ans,a[k].num+1); } } for(k=i;k<=j;k++) { if(a[k].y!=p) { zy.changemn(a[k].z+N,a[k].num); ny.changemn(N+1-a[k].z,a[k].num); } if(a[k].z!=q) { zz.changemn(a[k].y+N,a[k].num); nz.changemn(N+1-a[k].y,a[k].num); } } i=j+1; } ans--; int tot=0; char now='7'; for(i=1;i<n;i++) { if(s[i]==now) tot++; else { ans=max(ans,tot); tot=1; now=s[i]; } } ans=max(ans,tot); printf("%d",ans); }