[bzoj2733] [HNOI2012]永无乡

  写了线段树合并。。具体合并姿势和可并堆基本一样。。

 1 #include<cstdio>
 2 #include<iostream>
 3 #include<cstring>
 4 #include<algorithm>
 5 using namespace std;
 6 const int maxn=100233,mxnode=maxn*20;
 7 int lc[mxnode],rc[mxnode],sz[mxnode],tot;
 8 int rt[maxn],fa[maxn],size[maxn];
 9 int val[maxn],id[maxn];
10 int i,j,k,n,m,ans,P,K;
11
12 int ra;char rx;
13 inline int read(){
14     rx=getchar(),ra=0;
15     while(rx<‘0‘||rx>‘9‘)rx=getchar();
16     while(rx>=‘0‘&&rx<=‘9‘)ra*=10,ra+=rx-48,rx=getchar();return ra;
17 }
18
19 int merge(int x,int y,int a,int b){
20     if(!x||!y)return x|y;
21     sz[x]+=sz[y];if(a==b)return x;
22     int mid=a+b>>1;
23     lc[x]=merge(lc[x],lc[y],a,mid),rc[x]=merge(rc[x],rc[y],mid+1,b);
24     return x;
25 }
26 void query(int x,int a,int b){
27     if(a==b){ans=id[a];return;}
28     int mid=a+b>>1;
29     if(K<=sz[lc[x]])query(lc[x],a,mid);else K-=sz[lc[x]],query(rc[x],mid+1,b);
30 }
31 void build(int &x,int a,int b){
32     x=++tot,sz[x]=1;
33     if(a==b)return;
34     int mid=a+b>>1;
35     if(P<=mid)build(lc[x],a,mid);else build(rc[x],mid+1,b);
36 }
37
38 inline int getfa(int x){
39     return fa[x]!=x?fa[x]=getfa(fa[x]):x;
40 }
41 inline void con(int a,int b){
42     a=getfa(a),b=getfa(b);
43     if(a!=b)
44         fa[a]=b,rt[b]=merge(rt[b],rt[a],1,n),size[b]+=size[a];
45 }
46 int main(){
47     n=read(),m=read();
48     for(i=1;i<=n;i++)val[i]=read(),id[val[i]]=i,P=val[i],build(rt[i],1,n),fa[i]=i,size[i]=1;
49     for(i=1;i<=m;i++)con(read(),read());
50     m=read();char s[2];int x;
51     while(m--){
52         scanf("%s",s);
53         if(s[0]==‘B‘)con(read(),read());else{
54             x=getfa(read()),K=read();
55             if(size[x]>=K)query(rt[x],1,n);else ans=-1;
56             printf("%d\n",ans);
57         }
58     }
59     return 0;
60 }

时间: 2024-10-20 06:40:36

[bzoj2733] [HNOI2012]永无乡的相关文章

bzoj2733: [HNOI2012]永无乡(splay)

2733: [HNOI2012]永无乡 Time Limit: 10 Sec  Memory Limit: 128 MBSubmit: 3778  Solved: 2020 Description 永无乡包含 n 座岛,编号从 1 到 n,每座岛都有自己的独一无二的重要度,按照重要度可 以将这 n 座岛排名,名次用 1 到 n 来表示.某些岛之间由巨大的桥连接,通过桥可以从一个岛 到达另一个岛.如果从岛 a 出发经过若干座(含 0 座)桥可以到达岛 b,则称岛 a 和岛 b 是连 通的.现在有两

[BZOJ2733] [HNOI2012] 永无乡 (splay启发式合并)

Description 永无乡包含 n 座岛,编号从 1 到 n,每座岛都有自己的独一无二的重要度,按照重要度可 以将这 n 座岛排名,名次用 1 到 n 来表示.某些岛之间由巨大的桥连接,通过桥可以从一个岛 到达另一个岛.如果从岛 a 出发经过若干座(含 0 座)桥可以到达岛 b,则称岛 a 和岛 b 是连 通的.现在有两种操作:B x y 表示在岛 x 与岛 y 之间修建一座新桥.Q x k 表示询问当前与岛 x连通的所有岛中第 k 重要的是哪座岛,即所有与岛 x 连通的岛中重要度排名第 k

[BZOJ2733] [HNOI2012]永无乡(并查集 + 线段树合并)

传送门 一看到第k大就肯定要想到什么权值线段树,主席树,平衡树之类的 然后就简单了 用并查集判断连通,每个节点建立一颗权值线段树,连通的时候直接合并即可 查询时再二分递归地查找 时间复杂度好像不是很稳定...但hzwer都用这种方法水过.. 正解好像是平衡树+启发式合并,以后学TT #include <cstdio> #include <iostream> #define N 100001 int n, m, q, cnt; int a[N], f[N], sum[N * 20],

bzoj2733: [HNOI2012]永无乡(splay+启发式合并/线段树合并)

这题之前写过线段树合并,今天复习Splay的时候想起这题,打算写一次Splay+启发式合并. 好爽!!! 写了长长的代码(其实也不长),只凭着下午的一点记忆(没背板子...),调了好久好久,过了样例,submit,1A! 哇真的舒服 调试输出懒得删了QwQ #include<iostream> #include<cstdlib> #include<cstring> #include<cstdio> #include<queue> #include

【pb_ds】【平衡树启发式合并】【并查集】bzoj2733 [HNOI2012]永无乡

用并查集维护联通性.对每个联通块维护一个平衡树.合并时启发式合并.比较懒,用了pb_ds. 1 #include<cstdio> 2 #include<ext/pb_ds/assoc_container.hpp> 3 #include<ext/pb_ds/tree_policy.hpp> 4 using namespace std; 5 using namespace __gnu_cxx; 6 using namespace __gnu_pbds; 7 tree<

HNOI2012永无乡

[HNOI2012]永无乡 Description 永无乡包含 n 座岛,编号从 1 到 n,每座岛都有自己的独一无二的重要度,按照重要度可 以将这 n 座岛排名,名次用 1 到 n 来表示.某些岛之间由巨大的桥连接,通过桥可以从一个岛 到达另一个岛.如果从岛 a 出发经过若干座(含 0 座)桥可以到达岛 b,则称岛 a 和岛 b 是连 通的.现在有两种操作:B x y 表示在岛 x 与岛 y 之间修建一座新桥.Q x k 表示询问当前与岛 x连通的所有岛中第 k 重要的是哪座岛,即所有与岛 x

BZOJ 2733: [HNOI2012]永无乡(treap + 启发式合并 + 并查集)

不难...treap + 启发式合并 + 并查集 搞搞就行了 ---------------------------------------------------------------------------------------- #include<cstdio> #include<cstring> #include<algorithm> #include<iostream> #define rep(i, n) for(int i = 0; i &l

Bzoj 2733: [HNOI2012]永无乡 数组Splay+启发式合并

2733: [HNOI2012]永无乡 Time Limit: 10 Sec  Memory Limit: 128 MBSubmit: 3955  Solved: 2112[Submit][Status][Discuss] Description 永无乡包含 n 座岛,编号从 1 到 n,每座岛都有自己的独一无二的重要度,按照重要度可 以将这 n 座岛排名,名次用 1 到 n 来表示.某些岛之间由巨大的桥连接,通过桥可以从一个岛 到达另一个岛.如果从岛 a 出发经过若干座(含 0 座)桥可以到达

bzoj 2733: [HNOI2012]永无乡 离线+主席树

2733: [HNOI2012]永无乡 Time Limit: 10 Sec  Memory Limit: 128 MBSubmit: 1167  Solved: 607[Submit][Status] Description 永无乡包含 n 座岛,编号从 1 到 n,每座岛都有自己的独一无二的重要度,按照重要度可 以将这 n 座岛排名,名次用 1 到 n 来表示.某些岛之间由巨大的桥连接,通过桥可以从一个岛 到达另一个岛.如果从岛 a 出发经过若干座(含 0 座)桥可以到达岛 b,则称岛 a