HDU 2665 / POJ 2104 静态区间第k小 主席树
来源:互联网 发布:snh48是什么玩意知乎 编辑:程序博客网 时间:2024/06/15 02:13
HDU题目链接
POJ题目链接
很早就开始接触主席树,但一直没有真正理解其维护方式。
后来了解了权值线段树和zkw线段树后,再回头学习主席树,发现其实理解起来也是很简单的。
对于主席树的每一个节点,分别维护其左儿子节点的标号和右儿子节点的标号加上其维护区间的数的个数。
对于区间
然后利用差分思想查询即可。
代码:POJ:
#include<cstdio>#include<vector>#include<algorithm>using namespace std;inline 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-'0';ch=getchar();} return x*f;}const int A = 1e5 + 10;class Seg_Tree{public: int l_rt,r_rt,sum;}Tree[A*20];int a[A],root[A],n,m,tot;vector<int> v;int get_id(int x){return lower_bound(v.begin(),v.end(),x)-v.begin()+1;}void update(int l,int r,int &x,int y,int pos){ Tree[++tot] = Tree[y];Tree[tot].sum++;x = tot; if(l==r) return; int mid = (l+r)>>1; if(pos<=mid) update(l,mid,Tree[x].l_rt,Tree[y].l_rt,pos); else update(mid+1,r,Tree[x].r_rt,Tree[y].r_rt,pos);}int query(int l,int r,int x,int y,int k){ if(l == r) return l; int res = Tree[Tree[y].l_rt].sum - Tree[Tree[x].l_rt].sum; int mid = (l+r)>>1; if(res>=k) return query(l,mid,Tree[x].l_rt,Tree[y].l_rt,k); return query(mid+1,r,Tree[x].r_rt,Tree[y].r_rt,k-res);}int main(){ n=read();m=read();tot = 0; for(int i=1 ;i<=n ;i++){a[i]=read();v.push_back(a[i]);} sort(v.begin(),v.end());v.erase(unique(v.begin(),v.end()),v.end()); for(int i=1 ;i<=n ;i++) update(1,n,root[i],root[i-1],get_id(a[i])); for(int i=1 ;i<=m ;i++){ int x,y,k; x=read();y=read();k=read(); printf("%d\n",v[query(1,n,root[x-1],root[y],k)-1]); } return 0;}
HDU:
#include<cstdio>#include<vector>#include<cstring>#include<algorithm>using namespace std;inline 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-'0';ch=getchar();} return x*f;}const int A = 1e5 + 10;class Seg_Tree{public: int l_rt,r_rt,sum;}Tree[A*20];int a[A],root[A],n,m,tot;vector<int> v;void init(){ v.clear();tot = 0; memset(root,0,sizeof(root)); memset(Tree,0,sizeof(Tree));}int get_id(int x){return lower_bound(v.begin(),v.end(),x)-v.begin()+1;}void update(int l,int r,int &x,int y,int pos){ Tree[++tot] = Tree[y];Tree[tot].sum++;x = tot; if(l==r) return; int mid = (l+r)>>1; if(pos<=mid) update(l,mid,Tree[x].l_rt,Tree[y].l_rt,pos); else update(mid+1,r,Tree[x].r_rt,Tree[y].r_rt,pos);}int query(int l,int r,int x,int y,int k){ if(l == r) return l; int res = Tree[Tree[y].l_rt].sum - Tree[Tree[x].l_rt].sum; int mid = (l+r)>>1; if(res>=k) return query(l,mid,Tree[x].l_rt,Tree[y].l_rt,k); return query(mid+1,r,Tree[x].r_rt,Tree[y].r_rt,k-res);}int main(){ int T;T=read(); while(T--){ init(); n=read();m=read(); for(int i=1 ;i<=n ;i++){a[i]=read();v.push_back(a[i]);} sort(v.begin(),v.end());v.erase(unique(v.begin(),v.end()),v.end()); for(int i=1 ;i<=n ;i++) update(1,n,root[i],root[i-1],get_id(a[i])); for(int i=1 ;i<=m ;i++){ int x,y,k; x=read();y=read();k=read(); printf("%d\n",v[query(1,n,root[x-1],root[y],k)-1]); } } return 0;}
阅读全文
0 0
- HDU 2665 / POJ 2104 静态区间第k小 主席树
- HDU 2665 求静态区间的第k小值 主席树讲解。
- poj 2104 区间第K小 主席树入门题
- POJ 2104 K-th Number 主席树 静态区间第K大
- POJ 2104 K-th Number (主席树 静态区间第K大)
- poj 2104 K-th Number (静态区间第k大,主席树)
- POJ 2104 K-th Number 静态区间第k大 主席树
- POJ 2104 & HDU 2665 & POJ 2761 K-th Number (主席树入门题 区间第K大)
- 【POJ】2104 K-th Number 静态第K小——主席树
- poj 2104 K-th Number(主席树,静态第k小)
- poj 2104 查询区间第k小 主席树 (递归和非递归)模板
- 主席树模板 区间第k小
- poj 2104 区间第k大 主席树
- poj 2104 主席树(区间第k大)
- hdu 2665 区间第K大 主席树入门
- 主席树静态查找区间第k小模板(并没有杰少详细)即讲解
- 【主席树入门 && 区间内第k小的数】POJ
- poj2761&&poj2104 主席树(静态区间第K大)
- HDOJ HDU 1010 Tempter of the Bone
- MVP的实现,后续更新mvp和databinding结合
- ubuntu安装mysql
- H5前端性能测试点及优化方法
- windows下c++如何读取主机名
- HDU 2665 / POJ 2104 静态区间第k小 主席树
- 【学习笔记】你不得不知道的跨域小知识
- Centos5和6 启动流程和故障恢复
- C++拷贝构造函数详解
- Wordpress本地搭建和安装
- js提交form表单
- JAVA数据类型 与 MYSQL数据类型对照表
- SER2016 DIV1(Paint)
- Pycharm 自动补全