就不说题意了,毕竟中文的简单题意,很显然的线段树,用 lazy数组去维护一下区间被修改多少次,每次区间被修改,区间中1的个数就变成区间长度减去原来区间中1的个数,然后就能解决这道题了。
感觉洛谷评分有问题,这明明是道很简单的题,为什么这能是蓝题。状态太差了,我要刷题!!!
最后,代码:
#include<bits/stdc++.h>
using namespace std;
string str;
const int maxn=2e5+100;
int ans;
int tree[maxn<<2];
int lazy[maxn<<2];
void push_up(int tp,int x)
{
tree[x]=tree[tp]+tree[tp+1];
}
void push_down(int tp,int x,int l,int mid,int r)
{
lazy[tp]^=lazy[x];
lazy[tp+1]^=lazy[x];
lazy[x]=0;
tree[tp]=(mid-l+1)-tree[tp];
tree[tp+1]=(r-mid)-tree[tp+1];
}
void build(int l,int r,int x)
{
if(l==r)
{
if(str[l-1]=='1')
tree[x]=1;
return ;
}
int tp=x<<1;
int mid=l+r>>1;
build(l,mid,tp);
build(mid+1,r,tp+1);
push_up(tp,x);
}
void update(int l,int r,int x,int L,int R)
{
if(l>R||r<L)
return ;
if(L<=l&&R>=r)
{
lazy[x]^=1;
tree[x]=(r-l+1-tree[x]);
return ;
}
int tp=x<<1;
int mid=l+r>>1;
if(lazy[x])
{
push_down(tp,x,l,mid,r);
}
update(l,mid,tp,L,R);
update(mid+1,r,tp+1,L,R);
push_up(tp,x);
}
void query(int l,int r,int x,int L,int R)
{
if(l>R||r<L)
return ;
if(L<=l&&R>=r)
{
ans+=tree[x];
return ;
}
int tp=x<<1;
int mid=l+r>>1;
if(lazy[x])
{
push_down(tp,x,l,mid,r);
}
query(l,mid,tp,L,R);
query(mid+1,r,tp+1,L,R);
push_up(tp,x);
}
int main()
{
int n,m;
cin>>n>>m;
cin>>str;
build(1,n,1);
int opt,l,r;
for(int i=0;i<m;++i)
{
cin>>opt>>l>>r;
if(opt)
{
ans=0;
query(1,n,1,l,r);
cout<<ans<<endl;
}
else
{
update(1,n,1,l,r);
}
}
return 0;
}