zoukankan      html  css  js  c++  java
  • (2016北京集训十)【xsy1530】小Q与内存

    一道很有意思的神题~

    暴力平衡树的复杂度很对(并不),但是$2^{30}$的空间一脸屎

    这题的正解是一个类似线段树的数据结构,我觉得很有创新性Orz

    首先可以想到一种暴力就是用一个点代表一个区间,然后用链表维护这些点的集合,每次alloc操作就相当于割开未分配的区间,即增加了一个点,free操作就相当于合并。所以最多会产生$n$个点,单次操作$O(n)$,时间复杂度$O(n^2)$但是不满,貌似常数小就可以拿60;

    把这个集合看成一个序列的话,快速修改点的信息肯定会想到线段树,正解就是用线段树去维护这个“区间集合”;

    但是直接暴力线段树的话并不比平衡树优,需要用类似区间修改打懒标记的方法:如果一个点没被分割过,那就先打上标记,不实际创建它的儿子,到访问时才真正建出来,这样就能达到每次操作均摊$O(logn)$的复杂度。

    开始算了算$2^{30}$线段树需要一千多万个节点,觉得很虚,结果一看空间1G瞬间不虚。。。

    其实我一直很喜欢这种二叉结构,觉得很优美,写起来也很舒服。。。

    代码:

      1 #include<algorithm>
      2 #include<iostream>
      3 #include<cstring>
      4 #include<cstdio>
      5 #include<cmath>
      6 #include<queue>
      7 #define inf 2147483647
      8 #define eps 1e-9
      9 #define DCSB {puts("failed");continue;}
     10 using namespace std;
     11 typedef long long ll;
     12 struct node{
     13     int lc,rc,v,bit;
     14 }t[20000001];
     15 int T,n,op,p,q,rt,cnt,tot,rts[200001];
     16 void pd(int u){
     17     if(t[u].bit==-1)return;
     18     if(t[u].bit>0){
     19         t[u].lc=++cnt;
     20         t[u].rc=++cnt;
     21         t[t[u].lc].bit=t[t[u].rc].bit=t[u].bit-1;
     22         t[t[u].lc].v=t[t[u].rc].v=1<<(t[u].bit-1);
     23     }else t[u].lc=t[u].rc=-1;
     24     t[u].bit=-1;
     25 }
     26 int ins(int u,int p){
     27     int now=++cnt,ret=now;
     28     pd(u);
     29     while(t[u].lc!=-1){
     30         t[now].bit=-1;
     31         t[u].v-=p;
     32         t[now].v=p;
     33         if(p<t[t[u].lc].v){
     34             t[now].rc=0;
     35             now=t[now].lc=++cnt;
     36             u=t[u].lc;
     37         }else{
     38             p-=t[t[u].lc].v;
     39             t[now].lc=t[u].lc;
     40             t[now].rc=++cnt;
     41             t[u].lc=0;
     42             now=t[now].rc;
     43             u=t[u].rc;
     44         }
     45         pd(u);
     46     }
     47     t[u].v-=p;
     48     t[now].bit=-1;
     49     t[now].v=p;
     50     t[now].lc=-1;
     51     return ret;
     52 }
     53 int del(int u,int v){
     54     if(!u||!v)return u|v;
     55     if(t[u].lc!=-1){
     56         t[u].lc=del(t[u].lc,t[v].lc);
     57         t[u].rc=del(t[u].rc,t[v].rc);
     58     }
     59     t[u].v+=t[v].v;
     60     return u;
     61 }
     62 int calc(int u,int p){
     63     int ret=0;
     64     while(t[u].bit==-1&&t[u].lc!=-1){
     65         ret*=2;
     66         if(t[u].lc&&p<t[t[u].lc].v)u=t[u].lc;
     67         else{
     68             p-=t[t[u].lc].v;
     69             u=t[u].rc;
     70             ret++;
     71         }
     72     }
     73     if(t[u].bit==-1)return ret;
     74     else return ret*(1<<t[u].bit)+p;
     75 }
     76 int main(){
     77     scanf("%d",&T);
     78     while(T--){
     79         rt=cnt=1;
     80         t[1].bit=30;
     81         t[1].v=1<<30;
     82         tot=0;
     83         scanf("%d",&n);
     84         for(int i=1;i<=n;i++){
     85             scanf("%d",&op);
     86             if(op==1){
     87                 scanf("%d",&p);
     88                 rts[++tot]=0;
     89                 if(t[rt].v<p)DCSB
     90                 rts[tot]=ins(rt,p);
     91                 puts("ok");
     92             }
     93             if(op==2){
     94                 scanf("%d",&p);
     95                 if(p>tot||!rts[p])DCSB
     96                 rt=del(rt,rts[p]);
     97                 rts[p]=0;
     98                 puts("ok");
     99             }
    100             if(op==3){
    101                 scanf("%d%d",&p,&q);
    102                 if(p>tot||!rts[p]||q>=t[rts[p]].v)DCSB
    103                 printf("%d
    ",calc(rts[p],q));
    104             }
    105         }
    106     }
    107     return 0;
    108 }
  • 相关阅读:
    4.Windows下安装ZooKeeper
    3. ZAB与Paxos算法的联系与区别。
    2. ZooKeeper的ZAB协议。
    1. 初识ZooKeeper。
    27. Spring Boot 部署与服务配置
    26.SpringBoot事务注解详解
    25.Spring @Transactional工作原理
    24. Spring Boot 事务的使用
    罗辑思维CEO李天田:我们是这样玩儿公司的
    mysql中char,varchar与text类型的区别和选用
  • 原文地址:https://www.cnblogs.com/dcdcbigbig/p/9639709.html
Copyright © 2011-2022 走看看