![](https://img-blog.csdnimg.cn/20201014180756925.png?x-oss-process=image/resize,m_fixed,h_64,w_64)
树状数组
文章平均质量分 78
yrleep
大学毕业不久,ios游戏自由开发者。
展开
-
poj1389 Area of S…
这个是线段树的经典题目了。 求n个矩形的面积并。 解法:把y坐标离散化,输入的矩形转换成两条平行于y轴的线(然后按x坐标排序)分别为入边和出边,然后对y轴建立线段树,依次插入线段。这个做法文字不好解释,具体的看代码吧。 #include #include #include #include using namespace std; const int maxn=1101; int ans;原创 2013-04-14 19:40:02 · 562 阅读 · 0 评论 -
poj 2761
也是询问第k最小数的题目,但是因为询问的区间不存在包含关系,所以可以对区间排序,然后按照左端点的顺序依次把点加入树状数组中,二分出第k值#include #include #include #include using namespace std; const int maxn=1e5+9; int n,m; int f[maxn],a[maxn]; int tr[maxn]; struc原创 2013-08-08 22:59:38 · 897 阅读 · 0 评论 -
poj 1823 Hotel 线段树
这个题目意思很简单,就是求连续的最长段。 查询次数比较多,时间卡的比较紧 之前写了个k*logn*logn的,结果tle了,pushup的时候如果每次都修改到满节点时pushup的话,因为一个区间最多被分成logn次,加上每次pushup最多执行logn次操作,所以复杂度就高了 其实更简单一点的方法是当修改了一个节点的局部时,就重新修改该节点的值。这样复杂度就变低了,这样看起来,真的还是得多原创 2013-04-14 19:40:18 · 739 阅读 · 0 评论 -
poj 3667 hotel 线段树…
题目意思很简洁,就是多次查询连续空段n的最靠左区间,并覆盖,或者把某段变成空。 用线段树维护三个参数,lmaxn,rmax,max分别表示靠左最长连续,靠右最长连续,最长连续。 修改时,父节点的三个参数都能从子节点参数求得(具体看代码),查询时,也能由子节点和父节点的三个参数递归的得到解答。这个过程不是太好讲明白,得自己想,具体的看代码。 #include #incl原创 2013-04-14 19:40:20 · 519 阅读 · 0 评论 -
poj 2104 K-th Num…
题目意思非常很简单。给十万个数,每次询问一段连续区间的第k大值。询问次数达到5000次。 在线段树中搜索出来的题目,但是很明显,区间需要记录什么信息才可以查询第k大值就很不好想。 最后想到,只有把这一段中的每个数的大小编号记录才能满足要求,那么就是把这一段中的每个数排序,那么存储的空间就变成了nlogn,构树的时间复杂度也是nlogn,线段树支持一个查询。一段中小于等于tmp的原创 2013-04-14 19:40:13 · 512 阅读 · 0 评论 -
poj 1177 Picture 线段树加扫描线
求矩形周长的并 之前做过一个求矩形面积并的题目 用到了扫描线这种思想 这个题目可以照搬,作两次扫描线,一次x轴,一次y轴,同样标记入边,出边,当边是最外面的边时 周长就加上这条边的长度的两倍,入边标志为1,出边为-1,当加入边之后count==0,则表明了这条边是最外面的边。 看了解题报告,做法比较高效,一次扫描线就可以。下回再看。 #include #include #include原创 2013-04-14 19:40:11 · 550 阅读 · 0 评论 -
poj 2352 Stars 线段树
题目意思:按照y第一关键字,x第二关键字的顺序给你n个点,每个点的level值定义为x值和y值都不大于它的点的个数。要求输出各个level的点的个数。 由于已经排好序,所以每个点进来的时候以前出现的点x值不大于它的点的个数就是它的level值。 由于x,y的值最大只有32000.所以建一棵节点个数为32000的线段树,然后每个点就来的时候查询一下(0,x) 然后再更新一下就ok了。原创 2013-04-14 19:39:58 · 608 阅读 · 0 评论 -
poj 3321 Apple Tree 线段树
题目意思很简单: 给你一颗n个节点的树,每个节点开始有一个苹果,然后m次修改,每次修改使得某个节点的苹果改变,有变成没有,没有变成有。询问的是某个节点及其子树的苹果数目。 刚开始直接水,直接建树模拟,tle了,因为如果树的高度非常大的话,每次修改的复杂度是o(n)的。 然后改用线段树,每次询问一个区间的苹果数目,修改的是一个点的值。只要每科子树的节点编号是连续的就可以用线段树做了。原创 2013-04-14 19:39:52 · 567 阅读 · 0 评论 -
poj 3067 japan 树状数组
求逆序对的题目 上次求逆序对用了归并排序 这次就尝试了树状数组,感觉树状数组要好写些,速度应该也会比较快 题解 先对边按左排序,然后对右求逆序对 求逆序对的时候有一个需要注意的,同一个起点出发的不会造成交叉 所以先把同一个起点的店都先getsum(),然后再分别insert() #include #include #include using namespace std; int n,m,t原创 2013-04-14 19:37:05 · 1521 阅读 · 0 评论 -
poj 3225 Help with Intervals
题目意思不再重复了,有中文的题意 思路:区间的开和闭直接开两倍的点数就可以了,奇数的表示边界点,偶数的表示比边界点大一点点的点。 然后这几个操作总的是要做区间覆盖和区间抑或。 覆盖的话非常简单,不再叙述。 抑或的话最直接的想法就是找到相同的区间,然后再做抑或操作。就是找到一个满区间时,如果区间内的点不是全部为0或者全部为1,则继续向下找。直到找到都是相同的为止。原创 2013-04-14 19:40:26 · 534 阅读 · 0 评论 -
poj 3468 A Simple…
裸的线段树的题目,修改区间,查询区间。 #include #include #include #define ls t #define rs t #define midt (tr[t].l+tr[t].r)>>1 using namespace std; const int maxn=111111; long long a[maxn]; struct { int l,r;原创 2013-04-14 19:40:15 · 530 阅读 · 0 评论 -
poj 2182 Lost Cows 线段树
这个题目做的很差 先放着,以后再看 #include #include #include using namespace std; const int maxn=8888; struct { int l,r,sum; }tr[maxn*8]; int maketree(int t,int l,int r) { tr[t].l=l; tr[t].r=r;原创 2013-04-14 19:40:06 · 475 阅读 · 0 评论 -
poj 2886
模拟约瑟夫环 转化成求动态数据的第k值,然后就可以用树状数组加二分的办法来处理。 #include #include #include using namespace std; const int maxn=5e5+9; int ans[maxn],tr[maxn]; char name[maxn][15]; int a[maxn]; int cnt[maxn]; bool is[max原创 2013-08-09 13:21:18 · 726 阅读 · 0 评论