树剖 TLE 40 求助
查看原帖
树剖 TLE 40 求助
759015
awa2333楼主2022/11/11 18:56

AC了1、12、14~19,其他全部TLE

#include <iostream>
using namespace std;

using ll=long long;

constexpr ll maxn=100010;
ll to[maxn*2],nxt[maxn*2],head[maxn*2],counte;
ll siz[maxn],fa[maxn],son[maxn],top[maxn],dep[maxn],dfn[maxn],rnk[maxn],cnt;
ll a[maxn];
ll n,m;

struct vertex{
    ll l,r,lazy,flag;
    ll ans;
};

ll datas[maxn];
vertex tree[maxn*4];

ll parent(ll i){
    return i/2;
}
ll left(ll i){
    return i*2;
}
ll right(ll i){
    return i*2+1;
}
void build(ll i,ll l,ll r){
    tree[i].l=l;
    tree[i].r=r;
    if(l==r){
        tree[i].ans=datas[r];
        return;
    }
    ll mid=(l+r)/2;
    build(left(i),l,mid);
    build(right(i),mid+1,r);
    tree[i].ans=(tree[left(i)].ans+tree[right(i)].ans);
}
void pushdown(ll i){
    ll mid{(tree[i].l+tree[i].r)/2};
    tree[left(i)].lazy=1;
    tree[right(i)].lazy=1;
    tree[left(i)].flag=tree[i].flag;
    tree[right(i)].flag=tree[i].flag;
    tree[left(i)].ans=(tree[i].flag*(mid-tree[i].l+1));
    tree[right(i)].ans=(tree[i].flag*(tree[i].r-mid));
    tree[i].lazy=0;
}
void install(ll i,ll l,ll r){
    if(tree[i].r<=r&&tree[i].l>=l){
        tree[i].ans=(tree[i].r-tree[i].l+1);
        tree[i].flag=1;
        tree[i].lazy=1;
        return;
    }
    if(tree[i].lazy!=0){
        pushdown(i);
    }
    if(tree[left(i)].r>=l){
        install(left(i),l,r);
    }
    if(tree[right(i)].l<=r){
        install(right(i),l,r);
    }
    tree[i].ans=(tree[left(i)].ans+tree[right(i)].ans);
}
void uninstall(ll i,ll l,ll r){
    if(tree[i].r<=r&&tree[i].l>=l){
        tree[i].ans=0;
        tree[i].flag=0;
        tree[i].lazy=1;
        return;
    }
    if(tree[i].lazy!=0){
        pushdown(i);
    }
    if(tree[left(i)].r>=l){
        uninstall(left(i),l,r);
    }
    if(tree[right(i)].l<=r){
        uninstall(right(i),l,r);
    }
    tree[i].ans=(tree[left(i)].ans+tree[right(i)].ans);
}

void change(ll i,ll l,ll r,ll k){
    if(tree[i].r<=r&&tree[i].l>=l){
        tree[i].ans=k*(tree[i].r-tree[i].l+1);
        tree[i].lazy=k;
        return;
    }
    if(tree[i].lazy!=0){
        pushdown(i);
    }
    if(tree[left(i)].r>=l){
        change(left(i),l,r,k);
    }
    if(tree[right(i)].l<=r){
        change(right(i),l,r,k);
    }
    tree[i].ans=(tree[left(i)].ans+tree[right(i)].ans);
}
ll ask(ll i,ll l,ll r){
    ll t{};
    if(tree[i].r<=r&&tree[i].l>=l){
        return tree[i].ans;
    }
    if(tree[i].lazy!=0){
        pushdown(i);
    }
    if(tree[left(i)].r>=l){
        t+=ask(left(i),l,r);
    }
    if(tree[right(i)].l<=r){
        t+=ask(right(i),l,r);
    }
    return t;
}

void add(ll u,ll v){
    ++counte;
    to[counte]=v;
    nxt[counte]=head[u];
    head[u]=counte;
}


void dfs(ll x){
    son[x]=0;
    siz[x]=1;
    for(ll i=head[x];i;i=nxt[i]){
        ll y=to[i];
        if(!dep[y]){
            dep[y]=dep[x]+1;
            fa[y]=x;
            dfs(y);
            siz[x]+=siz[y];
            if(son[x]==0||siz[y]>siz[son[x]]){
                son[x]=y;
            }
        }
    }
}

void dfs(ll x,ll t){
    top[x]=t;
    ++cnt;
    dfn[x]=cnt;
    rnk[cnt]=x;
    if(son[x]==0){
        return;
    }
    dfs(son[x],t);
    for(ll i=head[x];i;i=nxt[i]){
        ll y=to[i];
        if(y!=son[x]&&y!=fa[x]){
            dfs(y,y);
        }
    }
}

void hld(){
    dep[1]=1;
    dfs(1);
    dfs(1,1);
}
ll lca(ll x,ll y){
    while(top[x]!=top[y]){
        if(dep[top[x]]<dep[top[y]]){
            y=fa[top[y]];
        }else{
            x=fa[top[x]];
        }
    }
    if(dep[x]<dep[y]){
        return x;
    }else{
        return y;
    }
}

int main(){
    cin.tie(nullptr);
    ios::sync_with_stdio(false);
    cin>>n;
    // for(ll i=1;i<=n;++i){
    //     cin>>a[i];
    // }
    for(ll i=1;i<=n-1;++i){
        ll x;
        cin>>x;
        add(x+1,i+1);
        add(i+1,x+1);
    }
    hld();
    // for(ll i=1;i<=n;++i){
    //     datas[dfn[i]]=a[i];
    // }
    build(1,1,n);
    cin>>m;
    // int dbg=0;
    for(ll i=1;i<=m;++i){
        string op;
        ll x;
        ll ans=0;
        cin>>op>>x;
        ++x;
        if(op=="install"){
            // if(dbg)cout<<"install "<<x-1<<" which depends on : ";
            if(ask(1,dfn[x],dfn[x])==0){
                while(x&&ask(1,dfn[top[x]],dfn[top[x]])==0){
                    for(int j=x;j!=fa[top[x]];j=fa[j]){
                        // if(dbg)cout<<"("<<x-1<<","<<j-1<<","<<ans<<") ";
                    }

                    ans+=dep[x]-dep[top[x]]+1;
                    // if(dbg)cout<<ans<<" ";
                    // change(1,dfn[top[x]],dfn[x],1);
                    install(1,dfn[top[x]],dfn[x]);
                    x=fa[top[x]];
                    // if(dbg)cout<<" , ";
                }
                // if(dbg)cout<<" ;("<<x-1<<","<<ask(1,dfn[x],dfn[x])<<") ";
                while(x&&ask(1,dfn[x],dfn[x])==0){
                    // if(dbg)cout<<x<<" ";
                    ++ans;
                    // change(1,dfn[x],dfn[x],1);
                    install(1,dfn[x],dfn[x]);
                    x=fa[x];
                }
                // if(dbg)cout<<endl;
            }
            cout<<ans<<"\n";
            // if(dbg)for(int j=1;j<=n;++j){
            //     cout<<ask(1,dfn[j],dfn[j])<<" ";
            // }
            // if(dbg)cout<<endl<<endl;
        }else{
            // if(dbg)cout<<"uninstall "<<x-1<<" that is "<<ask(1,dfn[x],dfn[x])<<" which is denpended on size of "<<siz[x]<<" on position of "<<dfn[x]<<endl;
            if(ask(1,dfn[x],dfn[x])==1){
                ans=ask(1,dfn[x],dfn[x]+siz[x]-1);
                // change(1,dfn[x],dfn[x]+siz[x]-1,0);
                uninstall(1,dfn[x],dfn[x]+siz[x]-1);
            }
            cout<<ans<<"\n";
            // if(dbg)for(int j=1;j<=n;++j){
            //     cout<<ask(1,dfn[j],dfn[j])<<" ";
            // }
            // if(dbg)cout<<endl<<endl;
        }
    }
}
2022/11/11 18:56
加载中...