区间not,求区间1的个数。。。线段树裸题
然而窝并不会线段树
我们可以对序列分块,每个块记录0/1的个数和tag表示又没有区间not过就好了
1 /************************************************************** 2 Problem: 1230 3 User: rausen 4 Language: C++ 5 Result: Accepted 6 Time:796 ms 7 Memory:1608 kb 8 ****************************************************************/ 9 10 #include <cstdio> 11 #include <cmath> 12 #include <algorithm> 13 14 using namespace std; 15 const int N = 1e5 + 5; 16 const int SZ = 505; 17 18 int n, m; 19 int a[N]; 20 int sz, b[N], st[SZ], cnt[SZ][2], tag[SZ], cnt_block; 21 22 inline int read() { 23 static int x; 24 static char ch; 25 x = 0, ch = getchar(); 26 while (ch < '0' || '9' < ch) 27 ch = getchar(); 28 while ('0' <= ch && ch <= '9') { 29 x = x * 10 + ch - '0'; 30 ch = getchar(); 31 } 32 return x; 33 } 34 35 inline void pre() { 36 int i; 37 sz = sqrt(n); 38 if (!sz) sz = 1; 39 for (i = 1; i <= n; ++i) { 40 if (i % sz == 1 || sz == 1) st[++cnt_block] = i; 41 b[i] = cnt_block, ++cnt[cnt_block][0]; 42 } 43 st[cnt_block + 1] = n + 1; 44 } 45 46 inline void push_tag(int B) { 47 static int i; 48 if (!tag[B]) return; 49 for (i = st[B]; i < st[B + 1]; ++i) 50 a[i] = !a[i]; 51 swap(cnt[B][0], cnt[B][1]); 52 tag[B] = 0; 53 } 54 55 inline void change(int x, int y) { 56 static int i, t1, t2; 57 t1 = b[x], t2 = b[y]; 58 for (i = t1 + 1; i < t2; ++i) tag[i] = !tag[i]; 59 if (t1 == t2) 60 for (push_tag(t1), i = x; i <= y; ++i) 61 --cnt[t1][a[i]], a[i] = !a[i], ++cnt[t1][a[i]]; 62 else { 63 for (push_tag(t1), i = x; i < st[t1 + 1]; ++i) 64 --cnt[t1][a[i]], a[i] = !a[i], ++cnt[t1][a[i]]; 65 for (push_tag(t2), i = st[t2]; i <= y; ++i) 66 --cnt[t2][a[i]], a[i] = !a[i], ++cnt[t2][a[i]]; 67 } 68 } 69 70 inline int query(int x, int y) { 71 static int i, t1, t2, res; 72 t1 = b[x], t2 = b[y], res = 0; 73 for (i = t1 + 1; i < t2; ++i) 74 res += cnt[i][!tag[i]]; 75 if (t1 == t2) 76 for (push_tag(t1), i = x; i <= y; ++i) res += a[i]; 77 else { 78 for (push_tag(t1), i = x; i < st[t1 + 1]; ++i) res += a[i]; 79 for (push_tag(t2), i = st[t2]; i <= y; ++i) res += a[i]; 80 } 81 return res; 82 } 83 84 int main() { 85 int i, oper, x, y; 86 n = read(), m = read(); 87 pre(); 88 for (i = 1; i <= m; ++i) { 89 oper = read(), x = read(), y = read(); 90 if (oper == 0) change(x, y); 91 else printf("%d\n", query(x, y)); 92 } 93 return 0; 94 }
By Xs酱~ 转载请说明
博客地址:http://www.cnblogs.com/rausen