点修改区间查询 HDU1166

 1 #include <iostream>
 2 #include <cstdio>
 3
 4 using namespace std;
 5
 6 int an[50010];
 7 struct Node
 8 {
 9     int l,r;
10     int v;
11 }bn[200000];
12
13 void build(int k,int l,int r)
14 {
15     bn[k].l=l;
16     bn[k].r=r;
17     if(l==r)
18     {
19         bn[k].v=an[l];
20         return ;
21     }
22     int lk=k*2;
23     int rk=lk+1;
24     int mid=(l+r)/2;
25     build(lk,l,mid);
26     build(rk,mid+1,r);
27     bn[k].v=bn[lk].v+bn[rk].v;
28 }
29
30 void change(int k,int i,int a)
31 {
32     if(bn[k].l==i&&bn[k].r==i)
33     {
34         bn[k].v+=a;
35         return ;
36     }
37     int lk=k*2;
38     int rk=lk+1;
39     if(i<=bn[lk].r)
40         change(lk,i,a);
41     else if(i>bn[k].l)
42         change(rk,i,a);
43     bn[k].v=bn[lk].v+bn[rk].v;
44 }
45
46 int search(int k,int l,int r)
47 {
48     if(bn[k].l==l&&bn[k].r==r)
49         return bn[k].v;
50     int lk=k*2;
51     int rk=lk+1;
52     if(bn[lk].r>=r)
53         search(lk,l,r);
54     else if(bn[rk].l<=l)
55         search(rk,l,r);
56     else
57         return search(lk,l,bn[lk].r)+search(rk,bn[rk].l,r);
58 }
59
60 int main()
61 {
62     int t;
63     cin>>t;
64     for(int l=1;l<=t;l++)
65     {
66         cout<<"Case "<<l<<":"<<endl;
67         int n;
68         scanf("%d",&n);
69         for(int i=1;i<=n;i++)
70             scanf("%d",&an[i]);
71         build(1,1,n);
72         char str[10];
73         int a,b;
74         while(scanf("%s",str)!=EOF)
75         {
76             if(str[0]==‘E‘)
77                 break;
78             scanf("%d%d",&a,&b);
79             if(str[0]==‘Q‘)
80             {
81                 cout<<search(1,a,b)<<endl;
82             }
83             else if(str[0]==‘A‘)
84             {
85                 change(1,a,b);
86             }
87             else if(str[0]==‘S‘)
88             {
89                 change(1,a,-b);
90             }
91         }
92     }
93     return 0;
94 }

时间: 2024-11-05 20:43:42

点修改区间查询 HDU1166的相关文章

【数据结构】线段树 (定义 &amp; 点修改/区间查询)

[本文描述高级数据结构线段树的定义] [并解决 点修改/区间查询 的问题] 结构与定义 线段树的基本结构 ? 由图可知,线段树的每一个节点都代表着一段区间 且同一层的节点(深度相同的节点)所表示的区间互不重叠 所有叶子节点代表的区间左边界与右边界相同(叶子节点代表单个元素) 普遍规定 如果某个非叶子节点代表的区间包含元素个数为奇数 则它的左儿子包含的元素个数比右儿子大 1 在代码部分,非叶子节点表示区间为 [l,r] 则左儿子为 [ l , (l+r)/2 ] ,右儿子为 [ (l+r)/2+1

树状数组 区间修改+区间查询

其实直到不久前都几乎不会用树状数组,请教了PPZ大佬之后终于懂了一点点. 然后小蒟蒻现在才知道了树状数组区间修改+区间查询的方法QAQ 传送门 Codevs 线段树练习3 //Twenty #include<cstdio> #include<cstdlib> #include<iostream> #include<algorithm> #include<cmath> #include<cstring> #include<queu

【bzoj3779】重组病毒 LCT+树上倍增+DFS序+树状数组区间修改区间查询

题目描述 给出一棵n个节点的树,每一个节点开始有一个互不相同的颜色,初始根节点为1. 定义一次感染为:将指定的一个节点到根的链上的所有节点染成一种新的颜色,代价为这条链上不同颜色的数目. 现有m次操作,每次为一下三种之一: RELEASE x:对x执行一次感染: RECENTER x:把根节点改为x,并对原来的根节点执行一次感染: REQUEST x:询问x子树中所有节点感染代价的平均值. 输入 输入的第一行包含两个整数n和m,分别代表局域网中计算机的数量,以及操作和询问的总数.接下来n-1行,

洛谷 P3374 【模板】树状数组 1 如题(单点修改+区间查询)

P3374 [模板]树状数组 1 时空限制1s / 128MB 题目描述 如题,已知一个数列,你需要进行下面两种操作: 1.将某一个数加上x 2.求出某区间每一个数的和 输入输出格式 输入格式: 第一行包含两个整数N.M,分别表示该数列数字的个数和操作的总个数. 第二行包含N个用空格分隔的整数,其中第i个数字表示数列第i项的初始值. 接下来M行每行包含3或4个整数,表示一个操作,具体如下: 操作1: 格式:1 x k 含义:将第x个数加上k 操作2: 格式:2 x y 含义:输出区间[x,y]内

二维树状数组模板(区间修改+区间查询)

二维树状数组模板(区间修改+区间查询) 例题:JOIOI上帝造题的七分钟 一共两种操作: \(L\ x_1\ y_1\ x_2\ y_2\ d\):把\((x_1,y_1)\),\((x_2,y_2)\)这个矩形内所有元素加\(d\). \(k\ x_1\ y_1\ x_2\ y_2\):查询\((x_1,y_1)\),\((x_2,y_2)\)这个矩形内所有元素的和. 代码如下: #include<bits/stdc++.h> #define RG register #define IL i

【bzoj5173】[Jsoi2014]矩形并 扫描线+二维树状数组区间修改区间查询

题目描述 JYY有N个平面坐标系中的矩形.每一个矩形的底边都平行于X轴,侧边平行于Y轴.第i个矩形的左下角坐标为(Xi,Yi),底边长为Ai,侧边长为Bi.现在JYY打算从这N个矩形中,随机选出两个不同的矩形,并计算它们的并的大小.JYY想知道,交的大小的期望是多少.换句话说即求在所有可能的选择中,两个矩形交的面积的平均大小是多大. 输入 输入一行包含一个正整数N. 接下来N行,每行4个整数,分别为Xi,Yi,Ai,Bi 2 < =  N < =  2*10^5, 0 < =  Xi,

树状数组的建树 单点修改 单点查询 区间修改 区间查询

单点修改  单点查询   用普通数组就能写出来 单点修改  区间查询   用线段树  树状数组: 区间修改  区间查询   用线段树  树状数组: 区间修改  单点查询   用线段树  树状数组: 建树 #include<bits/stdc++.h> using namespace std; const int maxn=1e5; struct node { int l,r,w; }tree[4*maxn+1]; void build(int l,int r,int k) { tree[k].

bzoj 3779 重组病毒 —— LCT+树状数组(区间修改+区间查询)

题目:https://www.lydsy.com/JudgeOnline/problem.php?id=3779 RELEASE操作可以对应LCT的 access,RECENTER则是 makeroot: 考虑颜色数,把一条实边变成虚边,子树+1,虚变实子树-1: 但有换根操作,怎么维护子树? 也可以用 dfs 序线段树维护,其实换 rt 只是 splay 的根方向改变,对应的子树还是可以找到的: 注意虚边变实或实边变虚时要找子树,不是直接找那个儿子,而是找那个儿子所在 splay 的根: 然后

树状数组实现区间修改+区间查询

事实上,这只是我弱弱的luogu博客的存档-- 线段树模板(1) 题意要求:给定一个序列,支持区间修改和区间查询. 智障数据结构模板题-- 当然,题目名字告诉我们要用线段树.但是线段树很长,容易出现问题,而且跑得稍慢,所以就有dalao开始yy:可不可以让树状数组支持区间修改和查询呢? 于是伟大的"超级树状数组"横空出世了. 首先,我们看树状数组是如何支持区间修改的: 设 tree[i]=a[i]-a[i-1] (差分),那么容易得到: tree[1]+tree[2]+--+tree[