Cogs 1345. [ZJOI2013] K大数查询(树套树)
来源:互联网 发布:乐知英语 编辑:程序博客网 时间:2024/06/05 16:08
- [ZJOI2013] K大数查询
/*树套树写法.bzoj过不了.可能有负数要离散吧.线段树套线段树.外层权值线段树,内层区间线段树维护标记.对权值建一棵权值线段树.某个点表示权值在某个范围内的数的个数.然后对每个点建一棵区间线段树.表示该权值范围在某个区间的数的个数.然后查找用类似二分的思想.*/#include<iostream>#include<cstdio>#define MAXN 50001using namespace std;struct data{int lc,rc,sum,size,bj;}tree[MAXN*400];int n,m,root[MAXN],cut;int read(){ int x=0,f=1;char ch=getchar(); while(ch<'0'||ch>'9'){if(ch=='-')f=-1;ch=getchar();} while(ch>='0'&&ch<='9') x=x*10+ch-48,ch=getchar(); return x*f;}void push(int k,int l,int r){ if(!tree[k].lc) tree[k].lc=++cut; if(!tree[k].rc) tree[k].rc=++cut; tree[tree[k].lc].bj+=tree[k].bj; tree[tree[k].rc].bj+=tree[k].bj; int mid=(l+r)>>1; tree[tree[k].lc].sum+=(mid-l+1)*tree[k].bj; tree[tree[k].rc].sum+=(r-mid)*tree[k].bj; tree[k].bj=0; return ;}void add(int &k,int l,int r,int x,int y){ if(!k) k=++cut; if(x==l&&r==y) { tree[k].bj++; tree[k].sum+=r-l+1; return ; } if(tree[k].bj) push(k,l,r); int mid=(l+r)>>1; if(y<=mid) add(tree[k].lc,l,mid,x,y); else if(x>mid) add(tree[k].rc,mid+1,r,x,y); else add(tree[k].lc,l,mid,x,mid),add(tree[k].rc,mid+1,r,mid+1,y); tree[k].sum=tree[tree[k].lc].sum+tree[tree[k].rc].sum; return ;}void sloveadd(int x,int y,int z)//先找到它所在权值的位置然后在[x,y]处加入贡献.{ int l=1,r=n,k=1,mid; while(l!=r) { mid=(l+r)>>1; add(root[k],1,n,x,y); if(z<=mid) r=mid,k=k<<1; else l=mid+1,k=(k<<1)+1; } add(root[k],1,n,x,y); return ;}int query(int k,int l,int r,int x,int y){ if(!k) return 0; if(tree[k].bj) push(k,l,r); if(x<=l&&r<=y) return tree[k].sum; int tot=0,mid=(l+r)>>1; if(x<=mid) tot+=query(tree[k].lc,l,mid,x,y); if(y>mid) tot+=query(tree[k].rc,mid+1,r,x,y); return tot;}int slovequery(int x,int y,int z){ int l=1,r=n,k=1; while(l!=r) { int mid=(l+r)>>1; int t=query(root[k<<1],1,n,x,y); if(t>=z) r=mid,k<<=1; else l=mid+1,k=(k<<1)+1,z-=t; } return l;}int main(){ freopen("zjoi13_sequence.in","r",stdin); freopen("zjoi13_sequence.out","w",stdout); int k,x,y,z; n=read(),m=read(); while(m--) { k=read(),x=read(),y=read(),z=read(); if(k&1) sloveadd(x,y,n-z+1); else printf("%d\n",n-slovequery(x,y,z)+1); } return 0;}
0 0
- Cogs 1345. [ZJOI2013] K大数查询(树套树)
- cogs 1345 [ZJOI2013] K大数查询
- [Zjoi2013]K大数查询
- [Zjoi2013]K大数查询 整体二分/树套树
- BZOJ 3110 ZJOI2013 K大数查询 树套树
- 【bzoj 3110】[Zjoi2013]K大数查询|树套树
- bzoj3110[ZJOI2013]K大数查询 树套树
- [BZOJ3110][Zjoi2013]-K大数查询-树套树
- 3110 [Zjoi2013]K大数查询
- bzoj3110 k大数查询 zjoi2013
- 【ZJOI2013】【BZOJ3110】K大数查询
- 3110: [Zjoi2013]K大数查询
- [BZOJ3110][Zjoi2013]K大数查询
- 3110: [Zjoi2013]K大数查询
- [BZOJ3110][Zjoi2013]K大数查询
- 【BZOJ3110】【ZJOI2013】K大数查询
- bzoj3110【ZJOI2013】K大数查询
- 【ZJOI2013&&BZOJ3110】K大数查询
- 1.1.1初识VisualBasic
- 位运算练习(1、将整数中的几位取出来,取反输出二进制2、将整数中间某一位置位 )
- 两个activity之间跳转会执行那几个方法
- hdu 2612Find a way 两次bfs+存表
- (4)AngularJS 1.X 之控制器
- Cogs 1345. [ZJOI2013] K大数查询(树套树)
- manjaro系统配置脚本
- ADRCI命令
- RxJava使用小总结:map家族
- (5)AngularJS 1.X 之事件指令
- Training2:位操作训练
- StringParser详解
- (6)AngularJS 1.X 与页面控制相关的指令
- 目前的一点感悟