Sequence operation

Time Limit: 10000/5000 MS (Java/Others)    Memory Limit: 32768/32768 K (Java/Others)
Total Submission(s): 8308    Accepted Submission(s): 2507

Problem Description
lxhgww got a sequence contains n characters which are all '0's or '1's.
We have five operations here:
Change operations:
0 a b change all characters into '0's in [a , b]
1 a b change all characters into '1's in [a , b]
2 a b change all '0's into '1's and change all '1's into '0's in [a, b]
Output operations:
3 a b output the number of '1's in [a, b]
4 a b output the length of the longest continuous '1' string in [a , b]
 
Input
T(T<=10) in the first line is the case number.
Each case has two integers in the first line: n and m (1 <= n , m <= 100000).
The next line contains n characters, '0' or '1' separated by spaces.
Then m lines are the operations:
op a b: 0 <= op <= 4 , 0 <= a <= b < n.
 
Output
For each output operation , output the result.
 
Sample Input
1
10 10
0 0 0 1 1 0 1 0 1 1
1 0 2
3 0 5
2 2 2
4 0 4
0 3 6
2 3 7
4 2 8
1 0 5
0 5 6
3 3 9
 
Sample Output
5
2
6
5
 
Author
lxhgww&&shǎ崽
及其恶心的一道题目,要维护许多变量= =
由于mx1函数写错找bug找了半天,最后发现自己的思路错了诶,可算A了。
中间维护的变量: 1的个数,0的个数,以第一个开始的最长连续0,以第一个开始的最长连续1,以最后一个开始的最长连续0,以最后一个开始的最长连续1,
区间最长连续1,区间最长连续0,可能有一些变量是互补的我写的有点多余不过感觉很方便把看起来,另外注意当操作为0/1时可以覆盖之前所有的标记。
我用0,1,2表示三种标记全0全1和翻转。len储存区间信息 一维表示'0'/'1'   二维表示 head,tail,max_continue_1  三维表示区间对应的结点值。
 #include<bits/stdc++.h>
using namespace std;
#define MAXN ((100000<<2)+15)
int g[][]={,,,,,,,,-};
struct SegmentTree
{
#define M ((L+R)>>1)
#define lc (id<<1)
#define rc (id<<1|1)
int num[MAXN][],X;
int len[][][MAXN];
short int laz[MAXN];
void show(int L,int R,int id)
{
if(L==R) {cout<<num[id][]<<" ";return;}
push_down(L,R,id);
show(L,M,lc);
show(M+,R,rc);
push_up(L,R,id);
}
void init()
{
memset(num,,sizeof(num));
memset(laz,-,sizeof(laz));
memset(len,,sizeof(len));
}
void push_up(int L,int R,int id)
{
num[id][]=num[lc][]+num[rc][];
num[id][]=num[lc][]+num[rc][];
for(int i=;i<=;++i){
len[i][][id]=len[i][][lc];
len[i][][id]=len[i][][rc];
len[i][][id]=max(max(len[i][][lc],len[i][][rc]),len[i][][lc]+len[i][][rc]);
if(!num[lc][i^]) len[i][][id]=max(len[i][][id],len[i][][lc]+len[i][][rc]);
if(!num[rc][i^]) len[i][][id]=max(len[i][][id],len[i][][rc]+len[i][][lc]);
}
}
void push_down(int L,int R,int id)
{
if(laz[id]==-) return;
laz[lc]=laz[lc]==-?laz[id]:g[laz[id]][laz[lc]];
laz[rc]=laz[rc]==-?laz[id]:g[laz[id]][laz[rc]];
if(laz[id]<){
num[lc][laz[id]^]=num[rc][laz[id]^]=;
num[lc][laz[id]]=M-L+;
num[rc][laz[id]]=R-M;
len[laz[id]^][][lc]=len[laz[id]^][][lc]=len[laz[id]^][][lc]=;
len[laz[id]^][][rc]=len[laz[id]^][][rc]=len[laz[id]^][][rc]=;
len[laz[id]][][lc]=len[laz[id]][][lc]=len[laz[id]][][lc]=M-L+;
len[laz[id]][][rc]=len[laz[id]][][rc]=len[laz[id]][][rc]=R-M;
}
else {
swap(num[lc][],num[lc][]);
swap(num[rc][],num[rc][]);
swap(len[][][lc],len[][][lc]); swap(len[][][lc],len[][][lc]); swap(len[][][lc],len[][][lc]);
swap(len[][][rc],len[][][rc]); swap(len[][][rc],len[][][rc]); swap(len[][][rc],len[][][rc]);
}
laz[id]=-;
}
void build(int L,int R,int id)
{
if(L==R)
{
scanf("%d",&X);num[id][X]++;
len[X][][id]=len[X][][id]=len[X][][id]=;
return;
}
build(L,M,lc);
build(M+,R,rc);
push_up(L,R,id);
}
void change(int L,int R,int id,int l,int r,int x)
{
if(L>=l&&R<=r){
num[id][x^]=;
num[id][x]=R-L+;
len[x][][id]=len[x][][id]=len[x][][id]=R-L+;
len[x^][][id]=len[x^][][id]=len[x^][][id]=;
laz[id]=laz[id]==-?x:g[x][laz[id]];
return;
}
push_down(L,R,id);
if(l<=M) change(L,M,lc,l,r,x);
if(r>M) change(M+,R,rc,l,r,x);
push_up(L,R,id);
}
void swp(int L,int R,int id,int l,int r)
{
if(L>=l&&R<=r){
swap(num[id][],num[id][]);
laz[id]=laz[id]==-?:g[][laz[id]];
swap(len[][][id],len[][][id]);
swap(len[][][id],len[][][id]);
swap(len[][][id],len[][][id]);
return;
}
push_down(L,R,id);
if(l<=M) swp(L,M,lc,l,r);
if(r>M) swp(M+,R,rc,l,r);
push_up(L,R,id);
}
int num1(int L,int R,int id,int l,int r)
{
if(L>=l&&R<=r) return num[id][];
push_down(L,R,id);
int s=;
if(l<=M) s+=num1(L,M,lc,l,r);
if(r>M) s+=num1(M+,R,rc,l,r);
push_up(L,R,id);
return s;
}
int mx1(int L,int R,int id,int l,int r)
{
if(L>=l&&R<=r) return len[][][id];
push_down(L,R,id);
int s=;
if(r<=M) s=max(s, mx1(L,M,lc,l,r));
else if(l>M) s=max(s,mx1(M+,R,rc,l,r));
else {
int lm=len[][][lc],rm=len[][][rc];
if(lm>M-l+) lm=M-l+;
if(rm>r-M) rm=r-M;
s=max(s,max(max(mx1(L,M,lc,l,r),mx1(M+,R,rc,l,r)),lm+rm));
}
push_up(L,R,id);
return s;
}
}seg; int main()
{
int t,n,m,i,j,k,opt,a,b;
scanf("%d",&t);
while(t--){
scanf("%d%d",&n,&m);
seg.init();
seg.build(,n,);
while(m--){
scanf("%d%d%d",&opt,&a,&b);a++;b++;
if(opt==) seg.change(,n,,a,b,);
else if(opt==) seg.change(,n,,a,b,);
else if(opt==) seg.swp(,n,,a,b);
else if(opt==) printf("%d\n",seg.num1(,n,,a,b));
else printf("%d\n",seg.mx1(,n,,a,b));
}
}
return ;
}

HDU 3397 线段树区间修改的更多相关文章

  1. E - Just a Hook HDU - 1698 线段树区间修改区间和模版题

    题意  给出一段初始化全为1的区间  后面可以一段一段更改成 1 或 2 或3 问最后整段区间的和是多少 思路:标准线段树区间和模版题 #include<cstdio> #include& ...

  2. HDU - 1698 线段树区间修改,区间查询

    这就是很简单的基本的线段树的基本操作,区间修改,区间查询,对区间内部信息打上laze标记,然后维护即可. 我自己做的时候太傻逼了...把区间修改写错了,对给定区间进行修改的时候,mid取的是节点的左右 ...

  3. Hdu 1698(线段树 区间修改 区间查询)

    In the game of DotA, Pudge's meat hook is actually the most horrible thing for most of the heroes. T ...

  4. hdu 1698 线段树 区间修改

    #include <cstdio> #include <cstdlib> #include <cmath> #include <map> #includ ...

  5. 题解报告:hdu 1698 Just a Hook(线段树区间修改+lazy懒标记的运用)

    Problem Description In the game of DotA, Pudge’s meat hook is actually the most horrible thing for m ...

  6. hdu 3397 线段树双标记

    Sequence operation Time Limit: 10000/5000 MS (Java/Others)    Memory Limit: 32768/32768 K (Java/Othe ...

  7. Codeforces Round #442 (Div. 2) E Danil and a Part-time Job (dfs序加上一个线段树区间修改查询)

    题意: 给出一个具有N个点的树,现在给出两种操作: 1.get x,表示询问以x作为根的子树中,1的个数. 2.pow x,表示将以x作为根的子树全部翻转(0变1,1变0). 思路:dfs序加上一个线 ...

  8. poj 2528 线段树区间修改+离散化

    Mayor's posters POJ 2528 传送门 线段树区间修改加离散化 #include <cstdio> #include <iostream> #include ...

  9. POJ 3667 & HDU 3308 & HDU 3397 线段树的区间合并

    看到讲课安排上 线段树有一节课"区间合并" 我是迷茫的 因为并没有见过 然后了解了一下题目 发现以前写过 还是很麻烦的树链剖分 大概是 解决带修改的区间查询"连续问题&q ...

随机推荐

  1. Python的数据类型和常用方法大全

    数据类型 一.数字 整形int x=10 #x=int(10) print(id(x),type(x),x) 浮点型float salary=3.1 #salary=float(3.1) print( ...

  2. CCF 字符串匹配(find()函数的使用)

    问题描述 试题编号: 201409-3 试题名称: 字符串匹配 时间限制: 1.0s 内存限制: 256.0MB 问题描述: 问题描述 给出一个字符串和多行文字,在这些文字中找到字符串出现的那些行.你 ...

  3. PL/SQL编程—存储过程

    SQL> create or replace procedure sp_pro3(name_in varchar2,id_in varchar2) is begin update mytest ...

  4. HDU 4746 Mophues(莫比乌斯反演)

    题意:求\(1\leq i \leq N,1\leq j \leq M,gcd(i,j)\)的质因子个于等于p的对数. 分析:加上了对质因子个数的限制. 设\(f(d):[gcd(i,j)=d]\) ...

  5. RedisTemplate和StringRedisTemplate

    最近在开始在学习Redis以及如何在Java当中去使用Redis,Redis是什么我这里就不说了. 我主要想说的是Redis和Java当中Spring结合起来的时候,使用到的RedisTemplate ...

  6. QML中的state 状态

    QML中的状态其实很好理解,任何事物在某一事件都是有一个状态的. 比如你看到的一个窗口,这个时候里面的文字和图片正处于某个状态中.比如一个超链接,你点击了,发现颜色变了,你按了Ctrl+A,整个窗体好 ...

  7. [Deep Learning]学习资料积累

    1. ufldl教程√ Andrew Ng的教程,matlab代码. 2. Neural Network and Deep Learning√: 一本未写完的书,非常细致,对基础的概念比如cross ...

  8. mysql搜索不区分大小写

    mysql搜索是不区分大小写的,这种情况下我们有两种方法解决 知识前提: BINARY binary不是函数,而是一个类型转换运算符,它用来强制字符串为一个二进制字符串,可以理解为在字符串比较的时候区 ...

  9. react native 0.56.0版本在windows下有bug不能正常运行

    react native的0.56.0版本在windows下有bug不能正常运行请init 0.55.4的版本 react-native init MyApp --version 0.55.4 注意v ...

  10. PayPal2019春招实习生笔试题的某一题

    题目简单描述:给你n个点的坐标(x, y),均为浮点数. 如果任意两个点之间的欧几里得距离小于给定的一个浮点值,则认为这两个点之间有关联,并且关联具有传递性,总之就是尽可能扩大一个集合. 输入: d ...