题目链接:http://poj.org/problem?id=3468

思路:如果直接去做,每次都更新到叶子节点,那必然会TLE,我们可以采用lazy的思想:没必要每次更新都更新到叶子节点,只要有一个合适的范围就用一个增量来记录它,当下一次询问时,如果这个范围正好合适询问的范围,就直接是这个节点的sum值加上这个区间长度*lnc,再加到总和上去,若这个节点的范围不适合所要查询的范围,那么就要查询它的子节点,这个时候再把增量传给她的子节点,并且清空父亲节点的增量,这样效率能大大提高。

 #include<iostream>
#include<cstdio>
#include<cstring>
#include<algorithm>
using namespace std;
#define MAXN 100010
typedef long long ll; struct Node{
int L,R;
ll lnc;//增量
ll sum;
}node[MAXN<<]; int N,Q; void Build(int L,int R,int rt)
{
if(L==R){
node[rt].lnc=node[rt].sum=;
return ;
}
node[rt].lnc=node[rt].sum=;
int M=(L+R)>>;
Build(L,M,rt<<);
Build(M+,R,(rt<<)|);
} void Updata(int L,int R,int rt,int id,ll x)
{
if(L==id&&R==id){
node[rt].sum=x;
return ;
}
node[rt].sum+=x;
int M=(L+R)>>;
if(id<=M){
Updata(L,M,rt<<,id,x);
}else
Updata(M+,R,(rt<<)|,id,x);
} void Add_Updata(int L,int R,int rt,int l,int r,ll x)
{
if(l<=L&&R<=r){
node[rt].lnc+=x;//若此节点所在区段被包含在要插入的区段中,就将插入值存在lnc中,return;
return ;
}else if(L<=l&&r<=R){
node[rt].sum+=(r-l+)*x;
}else if(L>=l&&R>=r){
node[rt].sum+=(r-L+)*x;
}else if(L<=l&&R<=r){
node[rt].sum+=(R-l+)*x;
}
int M=(L+R)>>;
if(r<=M){
Add_Updata(L,M,rt<<,l,r,x);
}else if(l>M){
Add_Updata(M+,R,(rt<<)|,l,r,x);
}else {
Add_Updata(L,M,rt<<,l,r,x);
Add_Updata(M+,R,(rt<<)|,l,r,x);
}
} ll sum;
void Query(int L,int R,int rt,int l,int r)
{
if(l<=L&&R<=r){
sum+=node[rt].sum+node[rt].lnc*(R-L+);
return ;
}
//若上面if条件不成立,则要询问它的子节点,此时增量要下传,并且要更新其本身的sum;
node[rt<<].lnc+=node[rt].lnc;
node[(rt<<)|].lnc+=node[rt].lnc;
node[rt].sum+=node[rt].lnc*(R-L+);
node[rt].lnc=;
int M=(L+R)>>;
if(r<=M){
Query(L,M,rt<<,l,r);
}else if(l>M){
Query(M+,R,(rt<<)|,l,r);
}else {
Query(L,M,rt<<,l,r);
Query(M+,R,(rt<<)|,l,r);
}
} int main()
{
int a,b,c;
char str[];
scanf("%d%d",&N,&Q);
Build(,N,);
for(int i=;i<=N;i++){
scanf("%d",&a);
Updata(,N,,i,(ll)a);
}
while(Q--){
scanf("%s",str);
if(str[]=='Q'){
scanf("%d%d",&a,&b);
sum=;
Query(,N,,a,b);
printf("%lld\n",sum);
}else {
scanf("%d%d%d",&a,&b,&c);
Add_Updata(,N,,a,b,(ll)c);
}
}
return ;
}

poj 3468(线段树+lazy思想)的更多相关文章

  1. poj 2777(线段树+lazy思想) 小小粉刷匠

    http://poj.org/problem?id=2777 题目大意 涂颜色,输入长度,颜色总数,涂颜色次数,初始颜色都为1,然后当输入为C的时候将x到y涂为颜色z,输入为Q的时候输出x到y的颜色总 ...

  2. POJ 2777——线段树Lazy的重要性

    POJ 2777 Count Color --线段树Lazy的重要性 原题 链接:http://poj.org/problem?id=2777 Count Color Time Limit: 1000 ...

  3. hdu 1698+poj 3468 (线段树 区间更新)

    http://acm.hdu.edu.cn/showproblem.php?pid=1698 这个题意翻译起来有点猥琐啊,还是和谐一点吧 和涂颜色差不多,区间初始都为1,然后操作都是将x到y改为z,注 ...

  4. poj 3468(线段树)

    http://poj.org/problem?id=3468 题意:给n个数字,从A1 …………An m次命令,Q是查询,查询a到b的区间和,c是更新,从a到b每个值都增加x.思路:这是一个很明显的线 ...

  5. C - A Simple Problem with Integers POJ - 3468 线段树模版(区间查询区间修改)

    参考qsc大佬的视频 太强惹 先膜一下 视频在b站 直接搜线段树即可 #include<cstdio> using namespace std; ; int n,a[maxn]; stru ...

  6. POJ 3468 线段树+状压

    题意:给你n个数,有对区间的加减操作,问某个区间的和是多少. 思路:状压+线段树(要用lazy标记,否则会TLE) //By SiriusRen #include <cstdio> #in ...

  7. POJ - 3468 线段树单点查询,单点修改区间查询,区间修改模板(求和)

    题意: 给定一个数字n,表示这段区间的总长度.然后输入n个数,然后输入q,然后输入a,b,表示查询a,b,区间和,或者输入c 再输入三个数字a,b,c,更改a,b区间为c 思路: 线段树首先就是递归建 ...

  8. POJ 3468 线段树裸题

    这些天一直在看线段树,因为临近期末,所以看得断断续续,弄得有些知识点没能理解得很透切,但我也知道不能钻牛角尖,所以配合着刷题来加深理解. 然后,这是线段树裸题,而且是最简单的区间增加与查询,我参考了A ...

  9. poj 3468 线段树区间更新/查询

    Description You have N integers, A1, A2, ... , AN. You need to deal with two kinds of operations. On ...

随机推荐

  1. ubuntu server获取并自动设置最快镜像的方法

    一,安装方法1 add-apt-repository ppa:ossug-hychen/getfastmirrorapt-get install getfastmirror 如果添加了临时源,这样移除 ...

  2. Knockout : 实现复杂的web聊天窗体

    公司以前一个同事写的这个聊天的窗体,由于是采用了html拼接的方式,外加处理的时候没有合理的划分职责,导致页面js代码量非常庞大(1500行左右).现在这哥们离职了,苦的是我们剩下的人,不多说,我先去 ...

  3. 扒一扒编辑距离(Levenshtein Distance)算法

    最近由于工作需要,接触了编辑距离(Levenshtein Distance)算法.赶脚很有意思.最初百度了一些文章,但讲的都不是很好,读起来感觉似懂非懂.最后还是用google找到了一些资料才慢慢理解 ...

  4. SQL Server数据库学习笔记-概念数据模型

    概念数据模型(Conceptual Data Model)也称为信息模型.它是对客观事物及其联系的抽象,用于信息世界的建模,是现实世界到信息世界的第一层抽象,是数据库设计人员进行数据库设计的有力工具. ...

  5. MS Chart-按照数据库的最大最小时间设置X轴label.

    核心代码: Chart1.ChartAreas[0].AxisX.Interval = (Front_Max - Front_Min).Days / 2; Chart1.ChartAreas[0].A ...

  6. Python实现kNN(k邻近算法)

    Python实现kNN(k邻近算法) 运行环境 Pyhton3 numpy科学计算模块 计算过程 st=>start: 开始 op1=>operation: 读入数据 op2=>op ...

  7. snmp4j 编程

    从www.snmp4j.org下载snmp4j的jar包,用eclipse新建一个java项目.将jar包导入工程(只有一个jar包),开始编程 一个简单的测试程序 //create target / ...

  8. Notes of the scrum meeting(11/2)

    meeting time:13:00~13:30p.m.,November 2nd,2013 meeting place:3号公寓楼一层 attendees: 顾育豪                  ...

  9. php调用微信发送自定义模版接口

     function sendWechatmodel($openid,$data,$go_url)//接受消息的用户openid,发送的消息,点击详情跳转的url        {           ...

  10. Careercup - Microsoft面试题 - 5649647234187264

    2014-05-10 22:17 题目链接 原题: A draw method is given, write a function to draw a chess board. The Draw m ...