警示后人/建议修改题解

P3369 【模板】普通平衡树


by keven___ @ 2024-02-04 09:19:00


/bx/bx/bx/bx
by KingPowers @ 2024-02-04 11:22:14


@[egg_rat](/user/672534) 建议 @ 一下管理员/题解作者
by AAA404 @ 2024-02-05 12:07:58


@[Maxmilite](/user/274993)
by egg_rat @ 2024-02-05 13:37:58


为啥我写 treap $\text{get\_rank}$ 返回 $0$ WA 了,但返回 $1$ AC?
by _zuoqingyuan @ 2024-02-13 22:02:23


@[_zuoqingyuan](/user/731650) 因为最后减了一,排除负无穷节点
by egg_rat @ 2024-02-17 10:16:27


```cpp #include <iostream> #include <cstdio> #include <cstdlib> using namespace std; const int N=1e5+10,inf=1e9+10;; int tot,root,n,op,x; struct node{ int l,r,cnt,size,dat,val; }a[N]; int New(int val){ a[++tot].val=val; a[tot].dat=rand(); a[tot].size=a[tot].cnt=1; return tot; } void update(int p){ a[p].size=a[a[p].l].size+a[a[p].r].size+a[p].cnt; } void build(){ root=New(-inf),a[root].r=New(inf); update(root); } void zig(int &p){//右旋 int q=a[p].l; a[p].l=a[q].r,a[q].r=p; p=q,update(p),update(a[p].r); } void zag(int &p){//左旋 int q=a[p].r; a[p].r=a[q].l,a[q].l=p; p=q;update(p),update(a[p].l); } void insert(int &p,int val){// 插入 if(!p){ p=New(val); return; }else if(a[p].val==val){ a[p].cnt++; update(p); return; } else if(a[p].val>val){ insert(a[p].l,val); if(a[p].dat<a[a[p].l].dat)zig(p); }else if(a[p].val<val){ insert(a[p].r,val); if(a[p].dat<a[a[p].r].dat)zag(p); } update(p); } void Delete(int &p,int val){// 删除 if(p==0)return; if(a[p].val==val){ if(a[p].cnt>1){ a[p].cnt--,update(p); return; } if(a[p].l||a[p].r){ if(a[p].r==0||a[a[p].l].dat>a[a[p].r].dat) zig(p),Delete(a[p].r,val); else zag(p),Delete(a[p].l,val); update(p); }else p=0; return; } a[p].val>val?Delete(a[p].l,val):Delete(a[p].r,val); update(p); } int get_rank(int p,int val,int f){//查排名 if(!p)return 1; else if(a[p].val==val)return a[a[p].l].size+1; else if(val<a[p].val)return get_rank(a[p].l,val,1); else return get_rank(a[p].r,val,2)+a[a[p].l].size+a[p].cnt; } int get_val(int p,int rank){// 查数 if(!p)return inf; else if(rank<=a[a[p].l].size)return get_val(a[p].l,rank); else if(rank<=a[a[p].l].size+a[p].cnt)return a[p].val; else return get_val(a[p].r,rank-a[p].cnt-a[a[p].l].size); } int get_pre(int val){//前倾 int ans=-inf,p=root; while(p){ if(a[p].val<val)ans=a[p].val,p=a[p].r; else p=a[p].l; } return ans; } int get_next(int val){//后继 int ans=inf,p=root; while(p){ if(a[p].val>val)ans=a[p].val,p=a[p].l; else p=a[p].r; } return ans; } int main(){ build(); scanf("%d",&n); while(n--){ scanf("%d %d",&op,&x); if(op==1)insert(root,x); if(op==2)Delete(root,x); if(op==3)printf("%d\n",get_rank(root,x,0)-1); if(op==4)printf("%d\n",get_val(root,x+1)); if(op==5)printf("%d\n",get_pre(x)); if(op==6)printf("%d\n",get_next(x)); } return 0; } ``` 我代码这么写 AC 了,就是及排除负无穷,$\text{get\_rank()}$ 没查到返回 $1$。离谱
by _zuoqingyuan @ 2024-02-17 10:38:21


|