HDU3397 Sequence Operation
来源:互联网 发布:部落冲突龙宝升级数据 编辑:程序博客网 时间:2024/06/05 13:33
题目链接:http://acm.hdu.edu.cn/showproblem.php?pid=3397
这道题是一个我认为非常非常麻烦的题,操作非常多,而且要打两个懒惰标记,并且懒惰标记有优先级之分,当一个节点收到一个覆盖标记的时候,取反标记就应该立即消失,这是一个麻烦,另外一个麻烦就是一个结点需要维持七个变量以满足本题的操作和所求。区间合并 的基本思想不用赘述,下面有一个成形的代码(貌似有bug),不过想法已经体现出来。
#include <iostream>#include <cstdio>#include <cstring>using namespace std;#define lson l, m, rt<<1#define rson m + 1, r, rt<<1|1const int maxn = 111111;int l1s[maxn<<2], r1s[maxn<<2], m1s[maxn<<2], l0s[maxn<<2], r0s[maxn<<2], m0s[maxn<<2], sum[maxn<<2];int cover[maxn<<2], col[maxn<<2];void PushDown(int rt, int m){ if (cover[rt] != -1){ cover[rt<<1] = cover[rt<<1|1] = cover[rt]; col[rt] = col[rt<<1] = col[rt<<1|1] = 0; l1s[rt<<1] = r1s[rt<<1] = m1s[rt<<1] = sum[rt<<1] = cover[rt] ? m - (m >> 1) : 0; l1s[rt<<1|1] = r1s[rt<<1|1] = m1s[rt<<1|1] = sum[rt<<1|1] = cover[rt] ? (m >> 1) : 0; l0s[rt<<1] = r0s[rt<<1] = m0s[rt<<1] = cover[rt] ? 0 : m - (m >> 1); l0s[rt<<1|1] = r0s[rt<<1|1] = m0s[rt<<1|1] = cover[rt] ? 0 : (m >> 1); cover[rt] = -1; } else if (col[rt]){ col[rt<<1] += col[rt]; col[rt<<1|1] += col[rt]; col[rt] %= 2; if (col[rt]){ swap(l1s[rt<<1], l0s[rt<<1]); swap(l1s[rt<<1|1], l0s[rt<<1|1]); swap(r1s[rt<<1], r0s[rt<<1]); swap(r1s[rt<<1|1], r0s[rt<<1|1]); swap(m1s[rt<<1], m0s[rt<<1]); swap(m1s[rt<<1|1], m0s[rt<<1|1]); sum[rt<<1] = (m - (m>>1)) - sum[rt<<1]; sum[rt<<1|1] = (m>>1) - sum[rt>>1|1]; } col[rt] = 0; }}void PushUp(int rt, int m){ l1s[rt] = l1s[rt<<1]; l0s[rt] = l0s[rt<<1]; r1s[rt] = r1s[rt<<1|1]; r0s[rt] = r0s[rt<<1|1]; if (l1s[rt] == m - (m >> 1)) l1s[rt] += l1s[rt<<1|1]; if (r1s[rt] == (m >> 1)) r1s[rt] += r1s[rt<<1]; if (l0s[rt] == m - (m >> 1)) l0s[rt] += l0s[rt<<1|1]; if (r0s[rt] == (m >> 1)) r0s[rt] += r0s[rt<<1]; m1s[rt] = max(l1s[rt<<1|1] + r1s[rt<<1], max(m1s[rt<<1], m1s[rt<<1|1])); m0s[rt] = max(l0s[rt<<1|1] + r0s[rt<<1], max(m0s[rt<<1], m0s[rt<<1|1])); sum[rt] = sum[rt<<1] + sum[rt<<1|1];}void build(int l, int r, int rt){ cover[rt] = -1; col[rt] = 0; if (l == r){ scanf("%d", &sum[rt]); l1s[rt] = r1s[rt] = m1s[rt] = cover[rt] = sum[rt]; l0s[rt] = r0s[rt] = m0s[rt] = 1 - sum[rt]; return; } int m = (l + r) >> 1; build(lson); build(rson); PushUp(rt, r - l + 1);}void update(int ll, int rr, int c, int l, int r, int rt){ if (ll <= l && rr >= r){ if (c == 2){ col[rt] += 1; sum[rt] = (r - l + 1) - sum[rt]; swap(m1s[rt], m0s[rt]); swap(l1s[rt], l0s[rt]); swap(r1s[rt], r0s[rt]); } else{ l1s[rt] = r1s[rt] = m1s[rt] = sum[rt] = c ? (r - l + 1) : 0; l0s[rt] = r0s[rt] = m0s[rt] = c ? 0 : r - l + 1; col[rt] = 0; cover[rt] = c; } } PushDown(rt, r - l + 1); int m = (l + r) >> 1; if (ll <= m) update(ll, rr, c, lson); if (rr > m) update(ll, rr, c, rson); PushUp(rt, r - l + 1);}int query_sum(int ll, int rr, int l, int r, int rt){ if (ll <= l && rr >= r) return sum[rt]; PushDown(rt, r - l + 1); int m = (l + r) >> 1; int ret = 0; if (ll <= m) ret += query_sum(ll, rr, lson); if (rr > m) ret += query_sum(ll, rr, rson); return ret;}int query_maxlen(int ll, int rr, int l, int r, int rt){ if (ll == l && rr == r) return m1s[rt]; PushDown(rt, r - l + 1); int m = (l + 1) >> 1; if (rr <= m) return query_maxlen(ll, rr, lson); else if (ll >= m) return query_maxlen(ll, rr, rson); else{ int a = query_maxlen(ll, m, lson); int b = query_maxlen(m+1, rr, rson); int c = 0; c += max(r1s[rt<<1], m - ll + 1); c += max(l1s[rt<<1|1], rr - m); return max(a, max(b, c)); }}int main(){ int t; scanf("%d", &t); while(t--){ int op, a, b; int n, m; scanf("%d%d", &n, &m); build(1, n, 1); while(m--){ scanf("%d%d%d", &op, &a, &b); a += 1; b += 1; if (op <= 2) update(a, b, op, 1, n, 1); else if (op == 3){ int ans = query_sum(a, b, 1, n, 1); printf("%d\n", ans); } else{ int ans = query_maxlen(a, b, 1, n, 1); printf("%d\n", ans); } } } return 0;}
- HDU3397 Sequence Operation
- HDU3397--Sequence operation
- HDU3397 Sequence operation
- hdu3397----Sequence operation
- hdu3397 Sequence operation
- hdu3397 Sequence operation
- HDU3397-Sequence operation
- HDU3397 Sequence operation(线段树)
- hdu3397 Sequence operation 线段树区间合并
- hdu3397 Sequence operation(线段树成段更新)
- HDU3397:Sequence operation(线段树区间合并)
- HDU3397(Sequence operation)线段树的多种操作
- HDU3397 Sequence operation(线段树的区间合并)
- hdu3397 Sequence operation--区间操作 & 双标记(待解决)
- HDU3397 Sequence operation 区间修改,区间异或,区间合并,线段树经典题
- hdu3397 Sequence operation 线段树区间更新&&bzoj1858: [Scoi2010]序列操作
- Sequence operation
- Sequence operation
- 黑马程序员java基础篇----集合总结
- 听道笔记-02.03.2013《让主居首位-重建祭坛与奉献生活的恢复》-于宏洁
- centos安装 python 2.7
- std::map使用出错_Nodeptr _Pnode = _Root();
- 听道笔记-02.10.2013《异象的动力》-陈道明
- HDU3397 Sequence Operation
- Android模拟器之间的网络通信及Ping主机
- HDU 2391
- 对LOWORD, HIWORD, LOBYTE, HIBYTE的理解
- 听道笔记-02.17.2013 戴继宗
- GDB 多线程调试
- java.lang.IndexOutOfBoundsException: Index: 0,Size
- 听道笔记-02.24.2013
- shift- add / shift or