线段树模版(转)
2015-08-10 18:23
330 查看
//=========================================== //segment tree //final version //by kevin_samuel(fenice)苏州大学孙俊彦 #include <iostream> #include <cstdio> #include <cmath> using namespace std; #define MAXN 100 #define INF 0x3fffffff int A[MAXN]; //int max; //int min; struct node { int left; int right; int max; //维护最大值 int sum; //维护区间和 int min; //维护最小值 }Tree[MAXN<<2]; void maintain(int root) //向上调整 { int LC = root<<1; int RC = (root<<1)+1; Tree[root].sum = Tree[LC].sum + Tree[RC].sum; Tree[root].max = max(Tree[LC].max,Tree[RC].max); Tree[root].min = min(Tree[LC].min,Tree[RC].min); } void Build(int root,int start,int end) //构建线段树 { Tree[root].left = start; Tree[root].right = end; if(start == end) { Tree[root].sum = A[start]; Tree[root].max = A[start]; Tree[root].min = A[start]; return; } int mid = (start + end)>>1; Build(root<<1,start,mid); Build((root<<1)+1,mid+1,end); maintain(root); } void update(int root,int pos,int value) //更新点的值 { if(Tree[root].left == Tree[root].right && Tree[root].left == pos) { Tree[root].sum += value; Tree[root].max += value; Tree[root].min += value; return; } int mid = (Tree[root].left + Tree[root].right)>>1; if(pos <= mid) update(root<<1,pos,value); else update((root<<1)+1,pos,value); maintain(root); } int Query(int root,int start,int end) //查询区间和 { if(start == Tree[root].left && Tree[root].right == end) { return Tree[root].sum; } int mid = (Tree[root].left + Tree[root].right)>>1; int ret = 0; if(end <= mid) ret += Query(root<<1,start,end); else if(start >= mid+1) ret += Query((root<<1)+1,start,end); else { ret += Query(root<<1,start,mid); ret += Query((root<<1)+1,mid+1,end); } return ret; } int RminQ(int root,int start,int end) //查询区间最小值 { if(start == Tree[root].left && Tree[root].right == end) { return Tree[root].min; } int mid = (Tree[root].left + Tree[root].right)>>1; int ret = INF; if(end <= mid) ret = min(ret,RminQ(root<<1,start,end)); else if(start >= mid+1) ret = min(ret,RminQ((root<<1)+1,start,end)); else { int a = RminQ(root<<1,start,mid); int b = RminQ((root<<1)+1,mid+1,end); ret = min(a,b); } return ret; } int RmaxQ(int root,int start,int end) //查询区间最大值 { if(start == Tree[root].left && Tree[root].right == end) { return Tree[root].max; } int mid = (Tree[root].left + Tree[root].right)>>1; int ret = 0; //modify this if(end <= mid) ret = max(ret,RmaxQ(root<<1,start,end)); else if(start >= mid+1) ret = max(ret,RmaxQ((root<<1)+1,start,end)); else { int a = RmaxQ(root<<1,start,mid); int b = RmaxQ((root<<1)+1,mid+1,end); ret = max(a,b); } return ret; } int main() { return 0; }
相关文章推荐
- POJ 3468 A Simple Problem with Integers (线段树,成段更新,区间求和)
- 关于jqGrid动态改变列的解决方案
- php5.3以上服务器单独安装php不安装mysql
- java 利用org.apache.poi.hssf包编写excel导出文件
- python 常用string函数
- (4.2.19)彩色进度条CircleProgress, DonutProgress, ArcProgress
- wcf生成代理类(SVCUtil.exe的用法)
- Android之Service例程
- json日期格式话
- Android基础:广播接收器及其生命周期介绍
- HDU3681Prison Break(BFS+TSP+二分+dp状态压缩)
- C语言-06-复杂数据类型
- 笔试测试题
- 线段树之HDU4614 Vases and Flowers
- 区间最小值(2) (线段树 更新区间)2015年 JXNU_ACS 算法组暑假第一次周赛
- 并查集的详解与应用(基础篇)
- HDOJ1466
- Android CircleProgressBar好看的圆形进度条
- 复制粘贴时导致eclipse(myeclipse、sts)卡死的解决办法
- Struts2 - 常用的constant总结