输入一串数字,有两个操作:Q a b 查询a到b区间内严格递增子串的最大长度 ; U a b 把第a位数字替换成b 。注意输入的编号是从0开始
解法:线段树维护区间的严格递增子串的最大长度即可。注意细节。
#include <iostream> #include <algorithm> #include <cstdio> #include <cstring>using namespace std; struct Tree{int l,r;int valuel,valuer,value;int ld,rd;}nod[100020<<2]; int n,m; int w[1000020] ;void Pushup(int k) {nod[k].valuel = nod[k].valuer = 1;if(nod[k<<1].rd < nod[k<<1|1].ld){nod[k].value=max(nod[k<<1].valuer+nod[k<<1|1].valuel,max(nod[k<<1].value,nod[k<<1|1].value));if(nod[k<<1].valuel == nod[k<<1].r-nod[k<<1].l+1 ){nod[k].valuel=nod[k<<1].valuel+nod[k<<1|1].valuel ;}if(nod[k<<1|1].valuer == nod[k<<1|1].r-nod[k<<1|1].l+1){nod[k].valuer=nod[k<<1|1].valuer+nod[k<<1].valuer;}nod[k].valuel=max(nod[k].valuel,nod[k<<1].valuel) ;nod[k].valuer=max(nod[k].valuer,nod[k<<1|1].valuer) ;//cout<<nod[2].valuer<<endl; }else{nod[k].value=max(nod[k<<1].value,nod[k<<1|1].value) ;nod[k].valuel = nod[k<<1].valuel ;nod[k].valuer = nod[k<<1|1].valuer ;}nod[k].ld=nod[k<<1].ld , nod[k].rd=nod[k<<1|1].rd ; }void Build(int l,int r,int k) {nod[k].l=l,nod[k].r=r , nod[k].ld=w[nod[k].l] , nod[k].rd=w[nod[k].r] ;if(nod[k].l == nod[k].r){nod[k].value= nod[k].valuel =nod[k].valuer= 1;return ;}int mid = (l+r)>>1 ;Build(l,mid,k<<1);Pushup(k) ;Build(mid+1,r,k<<1|1);Pushup(k); }int Query(int l,int r,int k) {int ans =0;if(nod[k].l==l && nod[k].r==r ){return nod[k].value ;}int mid=(nod[k].l + nod[k].r)>>1 ;if(r<=mid){return Query(l,r,k<<1) ;}else if(l>mid){return Query(l,r,k<<1|1) ;}else{if(nod[k<<1].rd < nod[k<<1|1].ld ){ans = max(Query(l,mid,k<<1) , Query(mid+1,r,k<<1|1)) ;int temp = min(mid-l+1,nod[k<<1].valuer)+min(r-(mid+1)+1,nod[k<<1|1].valuel) ;ans=max(ans,temp);}else{ans= max(Query(l,mid,k<<1),Query(mid+1,r,k<<1|1)) ;}}return ans ;}void Update(int l,int k,int value) {if(nod[k].l==nod[k].r && nod[k].l == l){nod[k].ld = nod[k].rd = value ;w[nod[k].r]=value ;nod[k].valuel = nod[k].valuer = nod[k].value =1 ;return ;}int mid=(nod[k].l+ nod[k].r)>>1 ;if(l<=mid){Update(l,k<<1,value);}else{Update(l,k<<1|1,value) ;}Pushup(k);return ;} int main() {int t;scanf("%d",&t) ;while(t--){scanf("%d%d",&n,&m) ;memset(w,0,sizeof w) ;for(int i=1;i<=n;i++){scanf("%d",&w[i]) ;}//getchar() ; Build(1,n,1) ;/*for(int i=1;i<=30;i++){cout<<i<<" "<<nod[i].value<<" "<<nod[i].valuel<<" "<<nod[i].valuer<<endl;}cout<<"-------------------------------------"<<endl;*/for(int i=0;i<m;i++){char c;int a,b;cin>>c;scanf("%d%d",&a,&b);//cout<<c<<endl;if(c=='Q'){a++,b++;if(a>b){swap(a,b) ;}int ans = Query(a,b,1);//cout<<c<<endl;printf("%d\n",ans) ;}else{a++;Update(a,1,b) ;/*for(int i=1;i<=30;i++){cout<<i<<" "<<nod[i].value<<" "<<nod[i].valuel<<" "<<nod[i].valuer<<endl;}cout<<"-------------------------------------"<<endl;*/}}}return 0; }