USACO 2008 Nov Gold 3.Light Switching 线段树
Code:
#include<cstdio>
#include<algorithm>
#include<cstring>
using namespace std;
const int maxn = 200000 + 4;
int lazy[maxn << 2], sumv[maxn << 2];
inline void pushdown(int o, int l,int r)
{
int ls = (o << 1), rs = (o << 1)|1, mid = (l + r) >> 1;
if(lazy[o])
{
lazy[ls] ^= 1, lazy[rs] ^= 1;
if(ls) sumv[ls] = (mid - l + 1) - sumv[ls];
if(rs) sumv[rs] = (r - mid) - sumv[rs];
lazy[o] = 0;
}
}
inline void pushup(int o){ sumv[o] = sumv[(o << 1)] + sumv[(o << 1)|1]; }
void update(int l,int r,int L,int R,int o)
{
if(r < L || l > R || l > r) return ;
if(l >= L && r <= R)
{
lazy[o] ^= 1, sumv[o] = (r - l + 1) - sumv[o];
return ;
}
int mid = (l + r) >> 1, ls = (o<<1), rs = (o<<1)|1;
pushdown(o, l, r);
update(l,mid, L,R,ls);
update(mid + 1, r, L, R ,rs);
pushup(o);
}
int query(int l,int r, int L,int R,int o)
{
if(l > r || r < L || l > R) return 0;
if(l >= L && r <= R) return sumv[o];
int mid = (l + r) >> 1, ls = (o << 1), rs = (o << 1)|1;
pushdown(o, l, r);
int tmp = 0;
tmp += query(l, mid, L, R, ls);
tmp += query(mid + 1, r, L, R, rs);
return tmp;
}
int main()
{
int n,m;
scanf("%d%d",&n,&m);
for(int i = 1;i <= m; ++i)
{
int ops, a, b;
scanf("%d%d%d",&ops,&a,&b);
if(ops == 0)update(1, n, a, b, 1);
if(ops == 1)printf("%d\n", query(1, n, a, b, 1));
}
return 0;
}