zoukankan      html  css  js  c++  java
  • bzoj3224 Tyvj 1728 普通平衡树

    Description

    您需要写一种数据结构(可参考题目标题),来维护一些数,其中需要提供以下操作:
    1. 插入x数
    2. 删除x数(若有多个相同的数,因只删除一个)
    3. 查询x数的排名(若有多个相同的数,因输出最小的排名)
    4. 查询排名为x的数
    5. 求x的前驱(前驱定义为小于x,且最大的数)
    6. 求x的后继(后继定义为大于x,且最小的数)

    Input

    第一行为n,表示操作的个数,下面n行每行有两个数opt和x,opt表示操作的序号(1<=opt<=6)

    Output

    对于操作3,4,5,6每行输出一个数,表示对应答案

    Sample Input

    10
    1 106465
    4 1
    1 317721
    1 460929
    1 644985
    1 84185
    1 89851
    6 81968
    1 492737
    5 493598

    Sample Output

    106465
    84185
    492737

    HINT

    1.n的数据范围:n<=100000
    2.每个数的数据范围:[-1e7,1e7]
    数据如下http://pan.baidu.com/s/1jHMJwO2

    正解:平衡树。

    这题就是平衡树,各种平衡树都能写。。今天晚上学了学替罪羊树,我能说我调了一晚上的原因是因为insert的传址问题吗。。

    替罪羊树:

      1 //It is made by wfj_2048~
      2 #include <algorithm>
      3 #include <iostream>
      4 #include <complex>
      5 #include <cstring>
      6 #include <cstdlib>
      7 #include <cstdio>
      8 #include <vector>
      9 #include <cmath>
     10 #include <queue>
     11 #include <stack>
     12 #include <map>
     13 #include <set>
     14 #define N (100010)
     15 #define il inline
     16 #define RG register
     17 #define ll long long
     18 #define File(s) freopen(s".in","r",stdin),freopen(s".out","w",stdout)
     19 
     20 using namespace std;
     21 
     22 int ch[N][2],cover[N],sz[N],val[N],del[N],st[N],Q,rt,top,tot;
     23 const double alpha=0.75;
     24 
     25 il int gi(){
     26     RG int x=0,q=1; RG char ch=getchar(); while ((ch<'0' || ch>'9') && ch!='-') ch=getchar();
     27     if (ch=='-') q=-1,ch=getchar(); while (ch>='0' && ch<='9') x=x*10+ch-48,ch=getchar(); return q*x;
     28 }
     29 
     30 il void pushup(RG int x){
     31     sz[x]=sz[ch[x][0]]+sz[ch[x][1]]+(!del[x]);
     32     cover[x]=cover[ch[x][0]]+cover[ch[x][1]]+1; return;
     33 }
     34 
     35 il void dfs(RG int x){
     36     if (ch[x][0]) dfs(ch[x][0]);
     37     if (!del[x]) st[++top]=x;
     38     if (ch[x][1]) dfs(ch[x][1]);
     39     sz[x]=cover[x]=ch[x][0]=ch[x][1]=0;
     40     return;
     41 }
     42 
     43 il int divide(RG int l,RG int r){
     44     if (l>r) return 0; RG int mid=(l+r)>>1;
     45     ch[st[mid]][0]=divide(l,mid-1);
     46     ch[st[mid]][1]=divide(mid+1,r);
     47     pushup(st[mid]); return st[mid];
     48 }
     49 
     50 il void rebuild(RG int &x){ top=0,dfs(x),x=divide(1,top); return; }
     51 
     52 il int qrank(RG int x,RG int k){
     53     RG int res=1;
     54     while (x){
     55     if (k<=val[x]) x=ch[x][0];
     56     else res+=sz[ch[x][0]]+(!del[x]),x=ch[x][1];
     57     }
     58     return res;
     59 }
     60 
     61 il int find(RG int x,RG int k){
     62     while (x){
     63     if (!del[x] && k==sz[ch[x][0]]+1) return val[x];
     64     if (k<=sz[ch[x][0]]) x=ch[x][0];
     65     else k-=sz[ch[x][0]]+(!del[x]),x=ch[x][1];
     66     }
     67     return val[x];
     68 }
     69 
     70 il int* Insert(RG int &x,RG int k){
     71     if (!x){ val[x=++tot]=k,sz[x]=cover[x]=1; return NULL; }
     72     sz[x]++,cover[x]++; int *p=Insert(ch[x][val[x]<=k],k);
     73     if (max(cover[ch[x][0]],cover[ch[x][1]])>cover[x]*alpha) p=&x;
     74     return p;
     75 }
     76 
     77 il void insert(RG int k){ int *x=Insert(rt,k); if (x) rebuild(*x); return; }
     78 
     79 il void Erase(RG int x,RG int k){
     80     while (x){
     81     sz[x]--; if (!del[x] && k==sz[ch[x][0]]+1){ del[x]=1; return; }
     82     if (k<=sz[ch[x][0]]) x=ch[x][0]; else k-=sz[ch[x][0]]+(!del[x]),x=ch[x][1];
     83     }
     84     return;
     85 }
     86 
     87 il void erase(RG int k){ Erase(rt,qrank(rt,k)); if (sz[rt]<cover[rt]*alpha) rebuild(rt); return; }
     88 
     89 il void work(){
     90     Q=gi(); RG int type,x;
     91     while (Q--){
     92     type=gi(),x=gi();
     93     if (type==1) insert(x);
     94     if (type==2) erase(x);
     95     if (type==3) printf("%d
    ",qrank(rt,x));
     96     if (type==4) printf("%d
    ",find(rt,x));
     97     if (type==5) printf("%d
    ",find(rt,qrank(rt,x)-1));
     98     if (type==6) printf("%d
    ",find(rt,qrank(rt,x+1)));
     99     }
    100     return;
    101 }
    102 
    103 int main(){
    104     File("tree");
    105     work();
    106     return 0;
    107 }

    最近又学了一下非旋转$treap$:

     1 #include <bits/stdc++.h>
     2 #define il inline
     3 #define RG register
     4 #define ll long long
     5 #define PR pair<int,int>
     6 #define inf (1<<30)
     7 #define N (100010)
     8 
     9 using namespace std;
    10 
    11 int val[N],key[N],sz[N],ls[N],rs[N],rt,n,tot;
    12 
    13 il int gi(){
    14   RG int x=0,q=1; RG char ch=getchar();
    15   while ((ch<'0' || ch>'9') && ch!='-') ch=getchar();
    16   if (ch=='-') q=-1,ch=getchar();
    17   while (ch>='0' && ch<='9') x=x*10+ch-48,ch=getchar();
    18   return q*x;
    19 }
    20 
    21 il void pushup(RG int x){
    22   sz[x]=sz[ls[x]]+sz[rs[x]]+1; return;
    23 }
    24 
    25 il int merge(RG int x,RG int y){
    26   if (!x || !y) return x|y;
    27   if (key[x]<key[y]){
    28     rs[x]=merge(rs[x],y),pushup(x); return x;
    29   } else{
    30     ls[y]=merge(x,ls[y]),pushup(y); return y;
    31   }
    32 }
    33 
    34 il PR split(RG int x,RG int k){
    35   if (!x) return make_pair(0,0); RG PR P;
    36   if (k<=sz[ls[x]]) P=split(ls[x],k),ls[x]=P.second,P.second=x;
    37   else P=split(rs[x],k-sz[ls[x]]-1),rs[x]=P.first,P.first=x;
    38   pushup(x); return P;
    39 }
    40 
    41 il int rk(RG int x,RG int k){
    42   RG int res=0,tmp=inf;
    43   while (x){
    44     if (k==val[x]) tmp=min(tmp,res+sz[ls[x]]+1);
    45     k<=val[x]?x=ls[x]:(res+=sz[ls[x]]+1,x=rs[x]);
    46   }
    47   return tmp==inf ? res : tmp;
    48 }
    49 
    50 il int find(RG int x,RG int k){
    51   if (k==sz[ls[x]]+1) return val[x];
    52   if (k<=sz[ls[x]]) return find(ls[x],k);
    53   return find(rs[x],k-sz[ls[x]]-1);
    54 }
    55 
    56 il int pre(RG int x,RG int k){
    57   if (!x) return -inf;
    58   if (k>val[x]) return max(val[x],pre(rs[x],k));
    59   return pre(ls[x],k);
    60 }
    61 
    62 il int nxt(RG int x,RG int k){
    63   if (!x) return inf;
    64   if (k<val[x]) return min(val[x],nxt(ls[x],k));
    65   return nxt(rs[x],k);
    66 }
    67 
    68 il void insert(RG int x){
    69   sz[++tot]=1,val[tot]=x,key[tot]=rand()<<15|rand();
    70   RG int k=rk(rt,x);
    71   RG PR P=split(rt,k);
    72   rt=merge(merge(P.first,tot),P.second);
    73 }
    74 
    75 il void del(RG int x){
    76   RG int k=rk(rt,x);
    77   RG PR P1=split(rt,k);
    78   RG PR P2=split(P1.first,k-1);
    79   rt=merge(P2.first,P1.second);
    80 }
    81 
    82 int main(){
    83 #ifndef ONLINE_JUDGE
    84   freopen("treap.in","r",stdin);
    85   freopen("treap.out","w",stdout);
    86 #endif
    87   srand(19260817); n=gi();
    88   for (RG int i=1,op,x;i<=n;++i){
    89     op=gi(),x=gi();
    90     if (op==1) insert(x); if (op==2) del(x);
    91     if (op==3) printf("%d
    ",rk(rt,x));
    92     if (op==4) printf("%d
    ",find(rt,x));
    93     if (op==5) printf("%d
    ",pre(rt,x));
    94     if (op==6) printf("%d
    ",nxt(rt,x));
    95   }
    96   return 0;
    97 }
  • 相关阅读:
    23种设计模式
    <转>企业应用架构 --- 分层
    <转>C/S架构分析
    Decorator 模式转载
    2019-10-24 体检结果备查,降甘油三脂药物
    Entity Framework Core 文档 & Core Web API 文档
    MSSQLLocalDB 微软本地数据库,pk SQLlite
    InstallWatch Pro
    学习 skoruba/ IdentityServer4.Admin 完整版
    无代码与低代码开发平台,云+本地,阿里/腾讯
  • 原文地址:https://www.cnblogs.com/wfj2048/p/6498757.html
Copyright © 2011-2022 走看看