咕咕了。。。于是借鉴了小粉兔的做法ORZ。。。


其实就是维护最大子段和的线段树,但上面又多了一些操作。。。。QWQ

维护8个信息:1/0的个数(sum),左/右边起1/0的最长长度(ls,rs),整段区间中1/0的连续最长长度(mx)。

于是对于各个操作,我们有了一些tag。。。

tg1[]是区间赋值标记,没有标记时为-1,有标记时为0或1;tg2[]是区间取反标记,没有标记时为 0,有标记时为1。

注意标记下传时要先传tg1[],再传tg2[],否则取反标记会被赋值标记覆盖

#include<cstdio>
#include<iostream>
#define R register int
#define ls (tr<<1)
#define rs (tr<<1|1)
const int N=;
using namespace std;
inline int g() {
R ret=,fix=; register char ch; while(!isdigit(ch=getchar())) fix=ch=='-'?-:fix;
do ret=ret*+(ch^); while(isdigit(ch=getchar())); return ret*fix;
}
int n,q,a[N];
struct node{
int sum0,sum1,ls0,ls1,rs0,rs1,mx0,mx1;
node(int s0=,int s1=,int ls0=,int ls1=,int rs0=,int rs1=,int mx0=,int mx1=):
sum0(s0),sum1(s1),ls0(ls0),ls1(ls1),rs0(rs0),rs1(rs1),mx0(mx0),mx1(mx1) {}
};
inline node upd(node l,node r) {
return node(l.sum0+r.sum0,l.sum1+r.sum1,
l.sum1?l.ls0:l.sum0+r.ls0,l.sum0?l.ls1:l.sum1+r.ls1,
r.sum1?r.rs0:r.sum0+l.rs0,r.sum0?r.rs1:r.sum1+l.rs1,
max(max(l.mx0,r.mx0),l.rs0+r.ls0),
max(max(l.mx1,r.mx1),l.rs1+r.ls1));
} node t[N]; int len[N],tg1[N],tg2[N];
inline void push(int tr,int typ) {
node& tmp=t[tr];
if(typ==) tg2[tr]=,tg1[tr]=,tmp=node(,len[tr],,len[tr],,len[tr],,len[tr]);
else if(typ==) tg2[tr]=,tg1[tr]=,tmp=node(len[tr],,len[tr],,len[tr],,len[tr],);
else if(typ==) tg2[tr]^=,swap(tmp.sum0,tmp.sum1),swap(tmp.ls0,tmp.ls1),swap(tmp.rs0,tmp.rs1),swap(tmp.mx0,tmp.mx1);
}
inline void spread(int tr) {
if(~tg1[tr]) push(ls,tg1[tr]),push(rs,tg1[tr]);
if(tg2[tr]) push(ls,),push(rs,);
tg1[tr]=-,tg2[tr]=;
}
inline void build(int tr,int l,int r) {
len[tr]=r-l+,tg1[tr]=-;
if(l==r) {R tmp=g(); t[tr]=node(tmp,tmp^,tmp,tmp^,tmp,tmp^,tmp,tmp^); return ;} R md=l+r>>;
build(ls,l,md),build(rs,md+,r); t[tr]=upd(t[ls],t[rs]);
}
inline void change(int tr,int l,int r,int LL,int RR,int d) {
if(LL<=l&&r<=RR) {push(tr,d); return ;} spread(tr); R md=l+r>>;
if(LL<=md) change(ls,l,md,LL,RR,d); if(RR>md) change(rs,md+,r,LL,RR,d);
t[tr]=upd(t[ls],t[rs]);
}
inline node query(int tr,int l,int r,int LL,int RR) {
if(LL<=l&&r<=RR) return t[tr]; spread(tr); R md=l+r>>; register node ret=node();
if(LL<=md) ret=query(ls,l,md,LL,RR); if(RR>md) ret=upd(ret,query(rs,md+,r,LL,RR)); return ret;
}
signed main() {
n=g(),q=g(); build(,,n);
for(R i=;i<=q;++i) {
R op=g(),l=g()+,r=g()+;
if(op<) change(,,n,l,r,op);
else {register node tmp=query(,,n,l,r); printf("%d\n",op==?tmp.sum0:tmp.mx0);}
}
}

2019.04.27

Luogu P2572 [SCOI2010]序列操作 线段树。。的更多相关文章

  1. 洛谷$P2572\ [SCOI2010]$ 序列操作 线段树/珂朵莉树

    正解:线段树/珂朵莉树 解题报告: 传送门$w$ 本来是想写线段树的,,,然后神仙$tt$跟我港可以用珂朵莉所以决定顺便学下珂朵莉趴$QwQ$ 还是先写线段树做法$QwQ$? 操作一二三四都很$eas ...

  2. 【题解】Luogu P2572 [SCOI2010]序列操作

    原题传送门:P2572 [SCOI2010]序列操作 这题好弱智啊 裸的珂朵莉树 前置芝士:珂朵莉树 窝博客里对珂朵莉树的介绍 没什么好说的自己看看吧 操作1:把区间内所有数推平成0,珂朵莉树基本操作 ...

  3. BZOJ 1858: [Scoi2010]序列操作( 线段树 )

    略恶心的线段树...不过只要弄清楚了AC应该不难.... ---------------------------------------------------------------- #inclu ...

  4. bzoj1858[Scoi2010]序列操作 线段树

    1858: [Scoi2010]序列操作 Time Limit: 10 Sec  Memory Limit: 64 MBSubmit: 3079  Solved: 1475[Submit][Statu ...

  5. 【bzoj1858】[Scoi2010]序列操作 线段树区间合并

    题目描述 lxhgww最近收到了一个01序列,序列里面包含了n个数,这些数要么是0,要么是1,现在对于这个序列有五种变换操作和询问操作: 0 a b 把[a, b]区间内的所有数全变成0 1 a b ...

  6. [SCOI2010]序列操作 线段树

    ---题面--- 题解: 在考场上打的这道题,出人意料的很快就打完了?! 直接用线段树,维护几个东西: 1,lazy标记 : 表示区间赋值 2,mark标记:表示区间翻转 3,l1:前缀最长连续的1的 ...

  7. bzoj1858 [Scoi2010]序列操作——线段树

    题目:https://www.lydsy.com/JudgeOnline/problem.php?id=1858 线段树...调了一个上午...(后面带 // 的都是改出来的) lazy 标记的下放好 ...

  8. P2572 [SCOI2010]序列操作

    对自己 & \(RNG\) : 骄兵必败 \(lpl\)加油! P2572 [SCOI2010]序列操作 题目描述 lxhgww最近收到了一个01序列,序列里面包含了n个数,这些数要么是0,要 ...

  9. 【题解】P4247 [清华集训]序列操作(线段树修改DP)

    [题解]P4247 [清华集训]序列操作(线段树修改DP) 一道神仙数据结构(DP)题. 题目大意 给定你一个序列,会区间加和区间变相反数,要你支持查询一段区间内任意选择\(c\)个数乘起来的和.对1 ...

随机推荐

  1. 使用laravel实现用户的登陆

    首先在 php artisan 里面 make:auth 生产一个门脸类 修改配置文件里面要哪个模型登陆 模型得继承一下才能 先写一下注册 密码必须要使用laravel的加密方法,使用MD5都没用 l ...

  2. WordPress 4.1去掉侧边栏“功能”小工具中WordPress.Org

    打开wp-includes/default-widgets.php,注释掉第398到第403行 echo apply_filters( 'widget_meta_poweredby', sprintf ...

  3. 171. Excel Sheet Column Number Excel表格的字母转成数字

    [抄题]: Given a column title as appear in an Excel sheet, return its corresponding column number. For ...

  4. Hibernate和Mybatis区别 详细 有用

    1.开发上手难度 hibernate的真正掌握(封装的功能和特性非常多)要比Mybatis来得难. 在真正产品级应用上要用Hibernate,不仅对开发人员的要求高,hibernate往往还不适合(多 ...

  5. File类中的list()和listFiles()方法

    list()方法是返回某个目录下的所有文件和目录的文件名,返回的是String数组 listFiles()方法是返回某个目录下所有文件和目录的绝对路径,返回的是File数组 public class  ...

  6. SVN下载地址及注意事项

    SVN下载地址:VisualSVN:http://www.visualsvn.com/server/download     服务器端(添加仓库和用户)TortoiseSVN:http://torto ...

  7. Robot Framework - 基础关键字 BuiltIn 库(一)

    今天给大家分享的是Robot Framework 机器人框架中 BuiltIn 基础库的使用...BuiltIn 库里面提供了很多基础方法助力于我们在自动化测试领域中做的更好!——本系列教程是教会大家 ...

  8. .net 3.5 Lambda表达式

    Lambda表达式 转自http://www.cnblogs.com/kingmoon/archive/2011/05/03/2035696.html "Lambda表达式"是一个 ...

  9. MVC区域路由配置

  10. C#多线程编程实战1.2暂停线程(休眠)

    using System;using System.Collections.Generic;using System.Linq;using System.Text;using System.Threa ...