poj2985线段树求第k大的数(并查集)
来源:互联网 发布:权力的游戏大麻雀知乎 编辑:程序博客网 时间:2024/05/29 03:22
Description
Newman likes playing with cats. He possesses lots of cats in his home. Because the number of cats is really huge, Newman wants to group some of the cats. To do that, he first offers a number to each of the cat (1, 2, 3, …,n). Then he occasionally combines the group cat i is in and the group cat j is in, thus creating a new group. On top of that, Newman wants to know the size of the k-th biggest group at any time. So, being a friend of Newman, can you help him?
Input
1st line: Two numbers N and M (1 ≤ N, M ≤ 200,000), namely the number of cats and the number of operations.
2nd to (m + 1)-th line: In each line, there is number C specifying the kind of operation Newman wants to do. If C = 0, then there are two numbers i and j (1 ≤ i, j ≤ n) following indicating Newman wants to combine the group containing the two cats (in case these two cats are in the same group, just do nothing); If C = 1, then there is only one number k (1 ≤ k ≤ the current number of groups) following indicating Newman wants to know the size of the k-th largest group.
Output
For every operation “1” in the input, output one number per line, specifying the size of the kth largest group.
Sample Input
10 100 1 21 40 3 41 20 5 61 10 7 81 10 9 101 1
Sample Output
12222
Hint
When there are three numbers 2 and 2 and 1, the 2nd largest number is 2 and the 3rd largest number is 1.
Source
//线段树每个节点维护的是group大小在这个区间的个数//每次更新时,包含a[x]和a[y] group大小的区间分别减1//而包含a[x]+a[y]的区间加1,询问的时候,先询问右子树//如果右子树的cnt>=k,则去右子树继续查询,否则去左子树//并且k-=rson的cnt。#include<iostream>#include<cstdio>#include<cstring>#include<algorithm>using namespace std;#define maxn 200005#define ls(o) o<<1#define rs(o) (o<<1)|1#define Mid(a,b) (a + b)>>1#define Fill(s,e,xx) for(int i=s;i<e;i++)a[i]=xx;int fa[maxn],Rank[maxn],n,m;void init(int n)//一定要记得初始化{ for(int i=0;i<=n;i++)fa[i]=i,Rank[i]=0;}int find_fa(int x)//查询是否已经在同一组了{ if(fa[x]!=x)fa[x]=find_fa(fa[x]); return fa[x];}void Union(int x,int y)//在这里并不需要这么合并,^-^,算是无用吧{ x = find_fa(x); y = find_fa(x); if(x==y)return; if(Rank[x]<Rank[y]){ fa[x] = y; } else{ fa[y] = x; if(Rank[x]==Rank[y])Rank[x]++; }}struct line_tree{ int l,r;//存储区间信息 int cnt;//存储在该区间内,有多少区间在该区间内的group}tree[maxn<<2];void build(int tl,int tr,int o){ tree[o].l=tl,tree[o].r=tr; if(tl==1)tree[o].cnt = n; else tree[o].cnt = 0; if(tl == tr){ return; } int mid = Mid(tl,tr); build(tl,mid,ls(o)); build(mid+1,tr,rs(o));}void Insert(int x,int o,int c){ tree[o].cnt+=c; if(tree[o].l == tree[o].r)return; if(x<=tree[ls(o)].r)Insert(x,ls(o),c); else Insert(x,rs(o),c);}int query(int k,int o=1){ if(tree[o].l==tree[o].r){ printf("%d\n",tree[o].l); return 0; } if(k<=tree[rs(o)].cnt)query(k,rs(o));//右子树有大于k个数,第k个数肯定在右边。。。。//求的是第k大数。。。。所以从右子树查询 else query(k-tree[rs(o)].cnt,ls(o));}int a[maxn];//存储group信息int main(){ while(scanf("%d%d",&n,&m)==2){ Fill(0,n+1,1); build(1,n,1);init(n); for(int i=0;i<m;i++){ int com; scanf("%d",&com); if(com==0){ int x,y; scanf("%d%d",&x,&y); x = find_fa(x),y=find_fa(y); if(x==y)continue; Insert(a[x],1,-1); Insert(a[y],1,-1); Insert(a[x]+a[y],1,1); fa[y] = x;//两个一定要一致。。。。。。。。。。 a[x]+=a[y]; } else{ int k; scanf("%d",&k); query(k); } } } return 0;}
- poj2985线段树求第k大的数(并查集)
- POJ2985 (线段树+并查集)
- poj2985 并查集+树状数组第k小
- POJ2985 The k-th Largest Group(treap+并查集)
- poj 2985 并查集+线段树 线段树求第k大数 The k-th Largest Group
- poj 2985 线段树求第k大的数
- poj 2985(并查集+线段树求K大数)
- The k-th Largest (并查集+线段树)
- POJ 题目2985 The k-th Largest Group(线段树单点更新求第k大值,并查集)
- 【bzoj4530】[Bjoi2014]大融合 并查集+线段树合并
- BJOI2014 大融合 并查集+线段树合并
- bzoj4530: [Bjoi2014]大融合 //线段树分治+并查集
- K大的 数
- poj 2985 The k-th Largest Group 并查集+树状数组求第k大
- PKU2985(The k-th Largest Group)线段树+并查集
- poj 2985 The k-th Largest Group(线段树+并查集)
- POJ2985 The k-th Largest Group(平衡树查询第K大)
- poj2985 The k-th Largest Group 【树状数组求第K大】
- 题目分类
- FZu 2134
- 模板 求凸包面积
- VMware安装64位系统注意事项
- 前端面试宝典——来自cnblog
- poj2985线段树求第k大的数(并查集)
- 黑马程序员--------------学习JAVA反射(Reflection)
- jQuery css() 方法
- 蛇形填数
- ThinkPHP 3.2.2 路由重写BUG ,修正方法
- grunt任务配置教程
- 102_widget的点击事件
- oracle的ora提示都是问号
- 关于java关键字synchronized的一些心得体会