poj3468A Simple Problem with Integers(线段树,在段更新时要注意)
Description
You have N integers, A1, A2, ... , AN. You need to deal with two kinds of operations. One type of operation is to add some given number to each number in a given interval. The other is to ask for the sum of numbers in a given interval.
Input
The first line contains two numbers N and Q. 1 ≤ N,Q ≤ 100000.
The second line contains N numbers, the initial values of A1, A2, ... , AN. -1000000000 ≤ Ai ≤ 1000000000.
Each of the next Q lines represents an operation.
"C a b c" means adding c to each of Aa, Aa+1, ... , Ab. -10000 ≤ c ≤ 10000.
"Q a b" means querying the sum of Aa, Aa+1, ... , Ab.
Output
You need to answer all Q commands in order. One answer in a line.
Sample Input
10 5
1 2 3 4 5 6 7 8 9 10
Q 4 4
Q 1 10
Q 2 4
C 3 6 3
Q 2 4
Sample Output
4
55
9
15
在段更新和查找时要注意,当父节点的下方和子节点的下方同时须要更新时不能直接覆盖了子节点的num,而是要加起来。
#include<iostream>
#include<stdio.h>
using namespace std;
#define N 100100
struct Tree
{
__int64 sum,num;//分别表示当前段的总和,子点的每个点所要加的值
bool b;//判断子节点是否要更新
}tree[4*N];
__int64 init[N+5];//初始时每个点的值
void builde(int l,int r,int k)
{
int m=(l+r)/2;
tree[k].b=false; tree[k].num=0;
if(l==r)
{
tree[k].sum=init[r]; return ;
}
builde(l,m,k*2);
builde(m+1,r,k*2+1);
tree[k].sum=tree[k*2].sum+tree[k*2+1].sum;
}
void set_child(int l,int r,int k)
{
int m=(l+r)/2;
if(tree[k*2].b==true)//注意这里,不能直接覆盖了
tree[k*2].num+=tree[k].num;
else
tree[k*2].num=tree[k].num;
tree[k*2].sum+=(m-l+1)*tree[k].num; if(tree[k*2+1].b==true)
tree[k*2+1].num+=tree[k].num;
else
tree[k*2+1].num=tree[k].num;
tree[k*2+1].sum+=(r-m)*tree[k].num;
tree[k*2].b=tree[k*2+1].b=true;
}
void updata(int l,int r,int k,int L,int R,__int64 num)
{
int m=(l+r)/2;
if(L<=l&&r<=R)
{
if(tree[k].b==true)
tree[k].num+=num;
else
tree[k].num=num;
tree[k].sum+=(r-l+1)*num;
tree[k].b=true;
return ;
}
if(tree[k].b==true)
set_child(l,r,k);
if(L<=m) updata(l,m,k*2,L,R,num);
if(R>m) updata(m+1,r,k*2+1,L,R,num);
tree[k].b=false;
tree[k].sum=tree[k*2].sum+tree[k*2+1].sum;
}
__int64 SUM;
void calculate(int l,int r,int k,int L,int R)
{
int m=(l+r)/2;
if(L<=l&&r<=R)
{
SUM+=tree[k].sum; return ;
}
if(tree[k].b==true)
set_child(l,r,k);
if(L<=m) calculate(l,m,k*2,L,R);
if(R>m) calculate(m+1,r,k*2+1,L,R);
tree[k].b=false;
}
int main()
{
int n,m,L,R,i;
__int64 num;
char ch[2];
scanf("%d%d",&n,&m);
for(i=1;i<=n;i++)
scanf("%I64d",&init[i]);
getchar();
builde(1,n,1);
while(m--)
{
scanf("%s%d%d",ch,&L,&R);
if(ch[0]=='Q')
{
SUM=0; calculate(1,n,1,L,R);
printf("%I64d\n",SUM);
}
else
{
scanf("%I64d",&num);
updata(1,n,1,L,R,num);
}
}
}
poj3468A Simple Problem with Integers(线段树,在段更新时要注意)的更多相关文章
- POJ3468_A Simple Problem with Integers(线段树/成段更新)
解题报告 题意: 略 思路: 线段树成段更新,区间求和. #include <iostream> #include <cstring> #include <cstdio& ...
- 【POJ】3468 A Simple Problem with Integers ——线段树 成段更新 懒惰标记
A Simple Problem with Integers Time Limit:5000MS Memory Limit:131072K Case Time Limit:2000MS Descr ...
- POJ 3468 A Simple Problem with Integers (线段树成段更新)
题目链接:http://poj.org/problem?id=3468 题意就是给你一组数据,成段累加,成段查询. 很久之前做的,复习了一下成段更新,就是在单点更新基础上多了一个懒惰标记变量.upda ...
- POJ 3468 A Simple Problem with Integers(线段树 成段增减+区间求和)
A Simple Problem with Integers [题目链接]A Simple Problem with Integers [题目类型]线段树 成段增减+区间求和 &题解: 线段树 ...
- A Simple Problem with Integers(线段树,区间更新)
A Simple Problem with Integers Time Limit: 5000MS Memory Limit: 131072K Total Submissions: 83822 ...
- 2018 ACMICPC上海大都会赛重现赛 H - A Simple Problem with Integers (线段树,循环节)
2018 ACM 国际大学生程序设计竞赛上海大都会赛重现赛 H - A Simple Problem with Integers (线段树,循环节) 链接:https://ac.nowcoder.co ...
- poj3468 A Simple Problem with Integers (线段树区间最大值)
A Simple Problem with Integers Time Limit: 5000MS Memory Limit: 131072K Total Submissions: 92127 ...
- POJ3648 A Simple Problem with Integers(线段树之成段更新。入门题)
A Simple Problem with Integers Time Limit: 5000MS Memory Limit: 131072K Total Submissions: 53169 Acc ...
- poj 3468 A Simple Problem with Integers 线段树第一次 + 讲解
A Simple Problem with Integers Description You have N integers, A1, A2, ... , AN. You need to deal w ...
随机推荐
- (六)6.11 Neurons Networks implements of self-taught learning
在machine learning领域,更多的数据往往强于更优秀的算法,然而现实中的情况是一般人无法获取大量的已标注数据,这时候可以通过无监督方法获取大量的未标注数据,自学习( self-taught ...
- c++ vector 释放内存
1.释放单个指针 关于Vector中存放指针的问题,在进行清空的时候比较安全的一种做法是: std::vector<ClassName *> ClassNameVec; ... ...
- 【UVa-679】小球下落——二叉树的编号
在结点1处放一个小球,它会往下落.每个内结点上都会有一个开关,初始全部关闭,当每次有小球落到一个开关上时,状态都会改变.当小球到达一个结点是,如果结点上的开关关闭,则往左走,否则往右走,直到走到叶子的 ...
- 构建高性能web站点--读书大纲
用户输入你的站点网址,等了半天..还没打开,裤衩一下就给关了.好了,流失了一个用户.为什么会有这样的问题呢.怎么解决自己站点“慢”,体验差的问题呢. 在这段等待的时间里,到底发生了什么?事实上这并不简 ...
- view的onFinishInflate()何时调用的?
onFinishInflate 当View中所有的子控件均被映射成xml后触发 比如你 自定义一个view叫myView ,路径是,com.test.view.MyView,此view是继承Linea ...
- OpenCV 连接 Android IP摄像头
0.下载IP摄像头(android软件)并安装 比如这个(图标是一个灰色的摄像头的那个软件) 1.新建cpp文件,编译 #include "opencv2/opencv.hpp" ...
- myeclipse安装
http://www.cnol.cc/2013/1427.html(我用这个) http://www.myeclipseide.cn/windows.html http://download.csdn ...
- Docker 基础技术:Linux Namespace(下)
导读 在Docker基础技术:Linux Namespace(上篇)中我们了解了,UTD.IPC.PID.Mount 四个namespace,我们模仿Docker做了一个相当相当山寨的镜像.在这一篇中 ...
- [Everyday Mathematics]20150301
设 $f(x)$ 在 $[-1,1]$ 上有任意阶导数, $f^{(n)}(0)=0$, 其中 $n$ 是任意正整数, 且存在 $C>0$, $$\bex |f^{(n)}(x)|\leq C^ ...
- cocos2d-x CCEditBox 字符不能显示完全的bug
cocos2d-x CCEditBox 字符不能显示完全的bug (cocos2dx版本 2.2.0)用CCEditBox制作帐号输入框,当输入的内容超过框的宽度时,框里面不会显示当前输入的字符,显示 ...