洛谷P3373 线段树2(补上注释了)
毒瘤题。找了一下午+晚上的BUG,才发现原来query_tree写的是a%p;
真的是一个教训
UPD:2019.6.18
#include<iostream>
#include<cmath>
#include<cstdio>
#include<cstring>
#include<queue>
#define lson i*2,l,mid //这个是宏定义,用前面的lson替代后面的i*2,l,mid
#define rson i*2+1,mid+1,r
using namespace std; struct tree{
long long mul; //mul是乘的缩写,add是加,sum是求和
long long add;
long long sum;
int l,r;
}t[]; int n,m,a[],p; void build_tree(int i,int l,int r)
{
t[i].l=l; //相乘的话必须是1,有大佬说l,r可以不定义,但是我码力不够
t[i].r=r;
t[i].mul=;
t[i].sum=;
t[i].add=;
if(l==r)
{
t[i].sum=a[l];
return ;
}
int mid=(l+r)/;
build_tree(lson);
build_tree(rson);
t[i].sum=(t[i*].sum+t[i*+].sum)%p;
} void pushdown2(int i) //回溯也有坑,大佬说两个push_down可以合并,特别注意mul最后赋值为1,向下传递的时候不要忘了下面的add和mul
{
t[i*].mul=t[i].mul*t[i*].mul%p;
t[i*+].mul=t[i].mul*t[i*+].mul%p;
t[i*].add=(t[i*].add*t[i].mul+t[i].add)%p;
t[i*+].add=(t[i*+].add*t[i].mul+t[i].add)%p;
t[i*].sum=(t[i].mul*t[i*].sum+t[i].add*(t[i*].r-t[i*].l+))%p;
t[i*+].sum=(t[i].mul*t[i*+].sum+t[i].add*(t[i*+].r-t[i*+].l+))%p;
t[i].add=;
t[i].mul=;
}
void pushdown(int i)
{
t[i*].mul=t[i].mul*t[i*].mul%p;
t[i*+].mul=t[i*+].mul*t[i].mul%p;
t[i*].add=(t[i*].add*t[i].mul+t[i].add)%p;
t[i*+].add=(t[i*+].add*t[i].mul+t[i].add)%p;
t[i*].sum=(t[i].mul*t[i*].sum+t[i].add*(t[i*].r-t[i*].l+))%p;
t[i*+].sum=(t[i].mul*t[i*+].sum+t[i].add*(t[i*+].r-t[i*+].l+))%p;
t[i].add=;
t[i].mul=;
}
void mul_tree(int i,int l,int r,int x,int y,int a)
{
if(l>=x&&r<=y)
{
t[i].sum*=a%p;
t[i].mul*=a%p;
t[i].add*=a%p;
return ;
}
pushdown(i);
int mid=(l+r)/;
if(x<=mid) mul_tree(lson,x,y,a);
if(y>mid) mul_tree(rson,x,y,a);
t[i].sum=(t[i*].sum+t[i*+].sum)%p;
}
void add_tree(int i,int l,int r,int x,int y,int a)
{
if(l>=x&&r<=y)
{
//t[i].mul*=a%p;
t[i].add+=a%p;
t[i].sum+=(t[i].r-t[i].l+)*a%p;
return ;
}
pushdown(i);
int mid=(l+r)/;
if(x<=mid) add_tree(lson,x,y,a);
if(y>mid) add_tree(rson,x,y,a);
t[i].sum=(t[i*].sum+t[i*+].sum)%p;
} int query_tree(int i,int l,int r,int a,int b)
{
if(l>=a&&r<=b) //l,r包含在ab区间则这一段直接返回
{
return t[i].sum%p;
}
int mid=(l+r)/;
long long ans=;
pushdown(i);
if(a<=mid) ans+=query_tree(lson,a,b)%p;
if(b>mid) ans+=query_tree(rson,a,b)%p;
return ans%p; }
int main()
{
scanf("%d %d %d",&n,&m,&p);
int i,j;
for(i=;i<=n;i++)
scanf("%d",&a[i]);
build_tree(,,n);
for(i=;i<=m;i++)
{
int k;
int t1,t2,t3;
scanf("%d",&k);
if(k==)
{
scanf("%d %d %d",&t1,&t2,&t3);
mul_tree(,,n,t1,t2,t3);
//printf("%d \n",query_tree(1,1,n,t1,t2)%p); //听说过复制粘贴吧
}
if(k==)
{
scanf("%d %d %d",&t1,&t2,&t3);
add_tree(,,n,t1,t2,t3);
//printf("%d \n",query_tree(1,1,n,t1,t2)%p);
}
if(k==)
{
scanf("%d %d",&t1,&t2);
printf("%d \n",query_tree(,,n,t1,t2)%p);
}
}
return ;
}
洛谷P3373 线段树2(补上注释了)的更多相关文章
- 洛谷P3373线段树模板2
题目:https://www.luogu.org/problemnew/show/P3373 带乘的线段树,更新时把加的标记也乘一下,然后取值时先乘后加. 代码如下: #include<iost ...
- 洛谷P3372线段树1
难以平复鸡冻的心情,虽然可能在大佬眼里这是水题,但对蒟蒻的我来说这是个巨大的突破(谢谢我最亲爱的lp陪我写完,给我力量).网上关于线段树的题解都很玄学,包括李煜东的<算法竞赛进阶指南>中的 ...
- NOIP2017提高组Day2T3 列队 洛谷P3960 线段树
原文链接https://www.cnblogs.com/zhouzhendong/p/9265380.html 题目传送门 - 洛谷P3960 题目传送门 - LOJ#2319 题目传送门 - Vij ...
- 洛谷 P3372 线段树1
这是一道模板题 线段树介绍https://www.cnblogs.com/nvwang123/p/10420832.html #include<bits/stdc++.h> using n ...
- 洛谷P3372线段树模板1——线段树
题目:https://www.luogu.org/problemnew/show/P3372 线段树模板. 代码如下: #include<iostream> #include<cst ...
- 洛谷3372线段树模板题 对区间+k或者查询区间和
#include<bits/stdc++.h> using namespace std; typedef unsigned int ui; typedef long long ll; ty ...
- 洛谷 P3373 【模板】线段树 2
洛谷 P3373 [模板]线段树 2 洛谷传送门 题目描述 如题,已知一个数列,你需要进行下面三种操作: 将某区间每一个数乘上 xx 将某区间每一个数加上 xx 求出某区间每一个数的和 输入格式 第一 ...
- 洛谷1087 FBI树 解题报告
洛谷1087 FBI树 本题地址:http://www.luogu.org/problem/show?pid=1087 题目描述 我们可以把由“0”和“1”组成的字符串分为三类:全“0”串称为B串,全 ...
- 洛谷P3018 [USACO11MAR]树装饰Tree Decoration
洛谷P3018 [USACO11MAR]树装饰Tree Decoration树形DP 因为要求最小,我们就贪心地用每个子树中的最小cost来支付就行了 #include <bits/stdc++ ...
随机推荐
- 暑期训练狂刷系列——poj 3468 A Simple Problem with Integers (线段树+区间更新)
题目连接: http://poj.org/problem?id=3468 题目大意: 给出n个数,有两种操作: 1:"C a b c",[a,b]中的每一个数都加上c. 2:&qu ...
- 贪心 Codeforces Round #173 (Div. 2) B. Painting Eggs
题目传送门 /* 题意:给出一种方案使得abs (A - G) <= 500,否则输出-1 贪心:每次选取使他们相差最小的,然而并没有-1:) */ #include <cstdio> ...
- Android 线程池系列教程(1)目录
Sending Operations to Multiple Threads 1.Dependencies and prerequisites Android 3.0 (API Level 11) o ...
- [转]C#委托Action、Action<T>、Func<T>、Predicate<T>
CLR环境中给我们内置了几个常用委托Action. Action<T>.Func<T>.Predicate<T>,一般我们要用到委托的时候,尽量不要自己再定义一 个 ...
- Android 轻松实现语音朗读
语音朗读,这是一个很好的功能,可以实现一些客户的特殊要求.在Android 实现主意功能只需要几段简单的代码即可完成. 在Android 中使用语音朗读功能 只需要使用此类 TextToSpeech ...
- linux下安装xampp
Choose your flavor for your linux OS, the 32-bit or 64-bit version. Change the permissions to the in ...
- 移动端展示pdf(在线打开pdf)
需求:在手机微信浏览器或者其他浏览器中打开pdf 准备:前端插件:查找pdf.js 官网地址:http://mozilla.github.io/pdf.js/ 在官网中下载demo 注释:pdf的d ...
- Farseer.net轻量级ORM开源框架 V1.x 入门篇:视图的数据操作
导航 目 录:Farseer.net轻量级ORM开源框架 目录 上一篇:Farseer.net轻量级ORM开源框架 V1.x 入门篇:视图实体类映射 下一篇:Farseer.net轻量级ORM开源 ...
- JavaScript中的跨域问题
跨域问题其实很普遍的存在的,如何解决跨域问题呢,跨域问题到底是怎么产生的,解决方法的由来又是什么?我觉得看了视频讲解,值得写下来,记录下来. 一.跨域问题是怎么产生? 概念:只要协议.域名.端口有任何 ...
- Oracle 学习之:ASCII,CHR函数的作用和用法
对于ASCII以及CHR函数的用法,Oracle给出的解释是: ASCII(x)gets the ASCII value of the character X, CHR() and ASCII() h ...