ZCMU-1156

image
image


思路:

  1. 要改变的是一个范围的情况,所以正常情况下会超时。
  2. 查阅后知道应该用一个叫做树状数组的结构。

查阅和树状数组的后续情况
这个也不错


注意:

  • 我没怎么看懂,可能没太仔细看。
  • 树状数组当中存在的是前后的差,所以每次变动只是在start,end+1变动.
  • 因为一直上去的是lowbit情况,方便后面前缀和。
  • 因为树状数组存放的不是本身的值,通过前缀和来求到。

#include<cstdio> 
#include<iostream>
#include<cstring>
using namespace std;
const int MAX=1000005;
int lan[MAX];
int n,m;
//树状数组的相关知识 
int lowbit(int x){
    return x&(-x);
}
//单点更新 
void update(int x,int val){
    for(int i=x;i<=n;i+=lowbit(i)){
        lan[i]+=val;
    }
}
//范围更新 
void range_update(int start,int end,int val){
    update(start,val);
    //其中树状数组存放的是前后的差。
    //在数里面修改和差为logN,没有遍历。 
    update(end+1,-val);
}
//前缀和 
int ask(int x){
    int sum=0;
    for(int i=x;i;i-=lowbit(i))
        sum+=lan[i];
        return sum;
}
int main(){
     
    while(~scanf("%d%d",&n,&m)){
        memset(lan,0,sizeof(lan));
        for(int i=0;i<m;i++){
            int flag,start,end;
             
            scanf("%d%d%d",&flag,&start,&end);
            //可能出现后大,题目没有告知谁大 
            if(start>end) swap(start,end);
             
            if(flag){
                range_update(start,end,1);
            }else{
                for(int j=start;j<=end;j++){
                    if(ask(j)&1)cout<<1;
                    else cout<<0; 
                }
                cout<<endl;
            }
        }
    }
    return 0;
}
posted @ 2024-05-20 18:38  海&贼  阅读(25)  评论(0)    收藏  举报