为啥会TLE?
查看原帖
为啥会TLE?
453460
End1essSummer楼主2022/9/12 19:50

RT 60pts TLE on #6 #7 #8 #9 #10

貌似是求krank的时候出错了 其中:

k-=tree[tree[u].son[0]].size+tree[u].cnt;

这一句话中的 tree[u].cnt 改成1后会WA,所以基本可以确定是这里出错了。

CODE:

#include<iostream>
#include<algorithm>
using namespace std;
#define int long long
const int N=1e6+10;
int n,root,cnt;
//save
struct poS/*potofSplay*/{
    int son[2],fa,val;
    int size,flag,cnt;
    void init(int VAL,int FA){
        val=VAL,fa=FA;
        size=cnt=1;
    }
}tree[N];
void update(int x){
    tree[x].size=tree[tree[x].son[0]].size+tree[tree[x].son[1]].size+tree[x].cnt;
}void rotate(int x){
    int y=tree[x].fa,z=tree[y].fa;
    int lr=tree[y].son[1]==x;//0l 1r
    tree[z].son[tree[z].son[1]==y]=x,tree[x].fa=z;
    tree[y].son[lr]=tree[x].son[lr^1],tree[tree[x].son[lr^1]].fa=y;
    tree[x].son[lr^1]=y,tree[y].fa=x;
    update(y),update(x);
}void splay(int x,int k){
    while(tree[x].fa!=k){
         //cout<<1<<' ';
        int y=tree[x].fa,z=tree[y].fa;
        if(z!=k){
            if((tree[z].son[1]==y)^(tree[y].son[1]==x)){
                rotate(x);
            }else{
                rotate(y);
            }
        }rotate(x);
    }if(!k) root=x;
}void ins(int v){
    int u=root,fa=0;
    while(u&&tree[u].val!=v){
        fa=u,u=tree[u].son[v>tree[u].val];
    }if(u){
        tree[u].cnt++;
    }else{
        u=++cnt;
        tree[u].cnt=1;
        if(fa){
            tree[fa].son[v>tree[fa].val]=u;
        }tree[u].init(v,fa);
    }splay(u,0);
}void Build(){
    for(int i=0;i<=n+1;i++){
        ins(i);
    }
}int getrank(int v){
    int u=root,ccnt=0;
    while(true){
        //cout<<u<<' '<<ccnt<<'\n';
        if(v<tree[u].val){
            u=tree[u].son[0];//find?yes
        }else{
            ccnt+=tree[tree[u].son[0]].size;
            if(v==tree[u].val){
                splay(u,0);
                return ccnt+1;
            }else{
                ccnt+=tree[u].cnt;
                u=tree[u].son[1];
            }
        }
    }
}int getkrank(int k){
    int u=root;
    while(true){
        if(tree[tree[u].son[0]].size>=k){
            u=tree[u].son[0];
        }else{
            if(tree[tree[u].son[0]].size+1==k){
                return tree[u].val;
            }else{
                k-=tree[tree[u].son[0]].size+tree[u].cnt;
                u=tree[u].son[1];
            }
        }
    }return -1;
}void Find(int x){
    int u=root;
    if(!u) return;
    while(tree[u].son[x>tree[u].val]&&x!=tree[u].val){
        u=tree[u].son[x>tree[u].val];
    }splay(u,0);
}int PreSuc(int x,int f){
    Find(x);
    int u=root;
    if((tree[u].val>x&&f)||(tree[u].val<x&&!f)) return u;
    u=tree[u].son[f];
    while(tree[u].son[f^1]) u=tree[u].son[f^1];
    return u;
}void Delete(int x){
    int last=PreSuc(x,0),next=PreSuc(x,1);
    splay(last,0);splay(next,last);
    int d=tree[next].son[0];
    if(tree[d].cnt>1){
        tree[d].cnt--;
        splay(d,0);
    }else{
        tree[next].son[0]=0;
    }
}signed main(){
    ins(1e9);ins(-1e9);
    cin>>n;
    while(n--){
        int opt,x;
        cin>>opt>>x;
        if(opt==1) ins(x);
        if(opt==2) Delete(x);
        if(opt==3) cout<<getrank(x)-1<<'\n';
        if(opt==4) cout<<getkrank(x+1)<<'\n';
        if(opt==5) cout<<tree[PreSuc(x,0)].val<<'\n';
        if(opt==6) cout<<tree[PreSuc(x,1)].val<<'\n';
    }
}
2022/9/12 19:50
加载中...