BZOJ1798 AHOI2009 维护数列
1798: [Ahoi2009]Seq 维护序列seq
Time Limit: 30 Sec Memory Limit: 64 MB
Description
Input
Output
Sample Input
1 2 3 4 5 6 7
5
1 2 5 5
3 2 4
2 3 7 9
3 1 3
3 4 7
Sample Output
35
8
HINT
【样例说明】
初始时数列为(1,2,3,4,5,6,7)。
经过第1次操作后,数列为(1,10,15,20,25,6,7)。
对第2次操作,和为10+15+20=45,模43的结果是2。
经过第3次操作后,数列为(1,10,24,29,34,15,16}
对第4次操作,和为1+10+24=35,模43的结果是35。
对第5次操作,和为29+34+15+16=94,模43的结果是8。
测试数据规模如下表所示
数据编号 1 2 3 4 5 6 7 8 9 10
N= 10 1000 1000 10000 60000 70000 80000 90000 100000 100000
M= 10 1000 1000 10000 60000 70000 80000 90000 100000 100000
迷醉线段树题。
这特么明显的线段树裸题,10w的数据,多组询问,支持区间修改和求和。
所以就是在lazy标记上做文章。
维护两个lazy标记,一个乘一个加。
因为要满足运算符优先级,所以乘法必须马上实现在加法上。
也就是说乘法的时候把加法的lazy也乘一遍。
所以lazy的乘法操作都是当前节点已经搞完了的。
那么lazy的下放就是要先乘再加了,不然会乘重复。
理清楚优先级的限制之后很好做的。(真的吗?)
反正我感觉乘的lazy就是加的lazy的lazy,除了一些维护答案的地方外... ...
感觉越说越不清楚,代码糊上。
#include <iostream>
#include <cstdio>
#include <cstdlib>
#include <algorithm>
#include <vector>
#include <cstring>
#include <queue>
#include <complex>
#include <stack>
#define ls (x<<1)
#define rs (x<<1|1)
#define LL long long int
#define dob double
using namespace std; const int N = 100010;
int n,P,m,T[N<<2],lazy_A[N<<2],lazy_M[N<<2]; int gi()
{
int x=0,res=1;char ch=getchar();
while(ch>'9'||ch<'0'){if(ch=='-')res*=-1;ch=getchar();}
while(ch<='9'&&ch>='0')x=x*10+ch-48,ch=getchar();
return x*res;
} inline void build(int x,int l,int r){
if(l==r){T[x]=gi();return;}
int mid=(l+r)>>1;
build(ls,l,mid);build(rs,mid+1,r);
T[x]=(T[ls]+T[rs])%P;
lazy_A[x]=0;lazy_M[x]=1;
} inline void down(int x,int l,int r){
int mid=(l+r)>>1;
T[ls]=(1ll*T[ls]*lazy_M[x]+1ll*(mid-l+1)*lazy_A[x])%P;
T[rs]=(1ll*T[rs]*lazy_M[x]+1ll*(r-mid)*lazy_A[x])%P;
lazy_M[ls]=(1ll*lazy_M[ls]*lazy_M[x])%P;
lazy_M[rs]=(1ll*lazy_M[rs]*lazy_M[x])%P;
lazy_A[ls]=(1ll*lazy_A[ls]*lazy_M[x]+1ll*lazy_A[x])%P;
lazy_A[rs]=(1ll*lazy_A[rs]*lazy_M[x]+1ll*lazy_A[x])%P;
lazy_A[x]=0;lazy_M[x]=1;
return;
} inline void Mul(int x,int l,int r,int xl,int xr,int v){
if(l==xl && r==xr){
lazy_A[x]=1ll*lazy_A[x]*v%P;
lazy_M[x]=1ll*lazy_M[x]*v%P;
T[x]=1ll*T[x]*v%P;
return;
}
down(x,l,r);
int mid=(l+r)>>1;
if(xr<=mid)Mul(ls,l,mid,xl,xr,v);
else if(xl>mid)Mul(rs,mid+1,r,xl,xr,v);
else Mul(ls,l,mid,xl,mid,v),Mul(rs,mid+1,r,mid+1,xr,v);
T[x]=(T[ls]+T[rs])%P;
} inline void Add(int x,int l,int r,int xl,int xr,int v){
if(l==xl && r==xr){
lazy_A[x]=(lazy_A[x]+v)%P;
T[x]=(1ll*T[x]+1ll*(r-l+1)*v)%P;
return;
}
down(x,l,r);
int mid=(l+r)>>1;
if(xr<=mid)Add(ls,l,mid,xl,xr,v);
else if(xl>mid)Add(rs,mid+1,r,xl,xr,v);
else Add(ls,l,mid,xl,mid,v),Add(rs,mid+1,r,mid+1,xr,v);
T[x]=(T[ls]+T[rs])%P;
} inline int query(int x,int l,int r,int xl,int xr){
if(l==xl && r==xr)return T[x];
down(x,l,r);
int mid=(l+r)>>1;
if(xr<=mid)return query(ls,l,mid,xl,xr);
else if(xl>mid)return query(rs,mid+1,r,xl,xr);
else return (query(ls,l,mid,xl,mid)+query(rs,mid+1,r,mid+1,xr))%P;
} int main()
{
n=gi();P=gi();
build(1,1,n);
m=gi();
while(m--){
int type=gi();
if(type==1){
int l=gi(),r=gi(),c=gi();
Mul(1,1,n,l,r,c);
}
if(type==2){
int l=gi(),r=gi(),c=gi();
Add(1,1,n,l,r,c);
}
if(type==3){
int l=gi(),r=gi();
printf("%d\n",query(1,1,n,l,r));
}
}
return 0;
}
BZOJ1798 AHOI2009 维护数列的更多相关文章
- bzoj1798 [Ahoi2009]维护序列
Description 老师交给小可可一个维护数列的任务,现在小可可希望你来帮他完成. 有长为N的数列,不妨设为a1,a2,…,aN .有如下三种操作形式: (1)把数列中的一段数全部乘一个值; (2 ...
- 【线段树】Bzoj1798 [AHOI2009] 维护序列
Description 老师交给小可可一个维护数列的任务,现在小可可希望你来帮他完成. 有长为N的数列,不妨设为a1,a2,…,aN .有如下三种操作形式: (1)把数列中的一段数全部乘一个值; (2 ...
- BZOJ1798[Ahoi2009]维护序列——线段树
题目描述 老师交给小可可一个维护数列的任务,现在小可可希望你来帮他完成. 有长为N的数列,不妨设为a1,a2,…,aN .有如下三种操作形式: (1)把数列中的一段数全部乘一个值; (2 ...
- BZOJ1798: [Ahoi2009]Seq 维护序列seq[线段树]
1798: [Ahoi2009]Seq 维护序列seq Time Limit: 30 Sec Memory Limit: 64 MBSubmit: 5504 Solved: 1937[Submit ...
- BZOJ_1798_[AHOI2009]维护序列_线段树
BZOJ_1798_[AHOI2009]维护序列_线段树 题意:老师交给小可可一个维护数列的任务,现在小可可希望你来帮他完成. 有长为N的数列,不妨设为a1,a2,…,aN .有如下三种操作形式: ( ...
- [洛谷P2023] [AHOI2009]维护序列
洛谷题目链接:[AHOI2009]维护序列 题目描述 老师交给小可可一个维护数列的任务,现在小可可希望你来帮他完成. 有长为N的数列,不妨设为a1,a2,-,aN .有如下三种操作形式: (1)把数列 ...
- 洛谷 P2023 [AHOI2009]维护序列
P2023 [AHOI2009]维护序列 题目描述 老师交给小可可一个维护数列的任务,现在小可可希望你来帮他完成. 有长为N的数列,不妨设为a1,a2,…,aN .有如下三种操作形式: (1)把数列中 ...
- 洛谷 P2023 [AHOI2009]维护序列 题解
P2023 [AHOI2009]维护序列 题目描述 老师交给小可可一个维护数列的任务,现在小可可希望你来帮他完成. 有长为N的数列,不妨设为a1,a2,-,aN .有如下三种操作形式: (1)把数列中 ...
- 【bzoj1500】 noi2005—维护数列
http://www.lydsy.com/JudgeOnline/problem.php?id=1500 (题目链接) 题意 要求维护数列,操作有区间删除,区间插入,区间反转,区间修改,区间求和,求最 ...
随机推荐
- 《HelloGitHub》第 20 期
前言 HelloGitHub 项目已经累积到 3k+ Stars.本项能够走到今天,帮助到越来越多的人.少不了热爱开源.不断为本项目贡献项目的小伙伴们. 贡献者列表 很多人都有想法,付诸于行动在少数, ...
- HTML Entity 字符实体
目录 1. HTML Entity 2. 字符与Entity Name的互相转换 3. 字符与Entity Number的互相转换 1. HTML Entity 1.1 介绍 在编写HTML页面时,需 ...
- Python 运行效率为何低
当我们提到一门编程语言的效率时:通常有两层意思,第一是开发效率,这是对程序员而言,完成编码所需要的时间:另一个是运行效率,这是对计算机而言,完成计算任务所需要的时间.编码效率和运行效率往往是鱼与熊掌的 ...
- .net 系列:Expression表达式树、lambda、匿名委托 的使用
首先定义一个泛型委托类型,如下: public delegate T Function<T>(T a, T b); 实现泛型委托的主体代码,并调用: public static strin ...
- 谈谈form-data请求格式
最近一直都比较忙,坚持月月更新博客的计划不得中止了,今天好不容易抽出点时间来说说最近项目中遇到的一个问题,有关request post请求格式中的multipart/form-data格式. 引言 最 ...
- mysql故障解决笔记
错误提示如图 一开始我查询了 [root@web01 mysql]# ls -al /lib/libc* -rwxr-xr-x 1 root root 1909464 Mar 22 01:49 /li ...
- JVM内存模型及垃圾回收的研究总结
Java内存模型 总的来说就分为两个区域,堆内存(Heap)和非堆内存(No-Heap),非堆内存又称为永久代(Permanent),永久的意思其实是针对于垃圾回收器来说的,表示这部分内容不需要回收. ...
- SQL Server Profiler的使用
最近一个项目,使用微软的Entity Framework的ORM框架的项目,部署到现场后,出现了系统缓慢,多个客户端的内存溢出崩溃的问题. 打开了SQL Server Profiler排查,发现有全表 ...
- inotify软件部署及实时同步
声明:博主使用的是CentOS6.9的系统 参考资料: https://github.com/rvoicilas/inotify-tools/wiki http://www.ibm.com/devel ...
- 【本地资源路径&&网络资源路径&&正反斜杠在Java中的用法】
一.概念和用法 左正右反 先来看看转义字符的概念:通过 \ ,?来转变后面字母或符号的含义.意思就是改变字母本身的含义. 以"\"符号为例,JAVA中有很多操作,例如文件操作等,需 ...