90pts求调
查看原帖
90pts求调
1602807
jokersen楼主2025/8/1 21:08

用的是莫队+值域分块,WA on #1。

#include<bits/stdc++.h>
#ifdef WIN32
#define getc() getchar()
#else
#define getc() getchar_unlocked()
#endif
#define N 80005
using namespace std;
struct query{
    int k,l,r,t,id;
}q1[N];
struct update{
    int p,c;
}q2[N];
int n,m,q,block_size,B,len,ccnt,qcnt,rcnt,size;
int h[N],a[N<<1],c[N<<1],f[N],g[N],fa[N][25],dep[N],cnt1[405],cnt2[N<<1],ans[N];
vector<int>s[N];
bitset<N<<1>vis;
void read(int &n){
    n=0;bool neg=false;
    char c=getc();
    while(c<'0'||c>'9') neg^=c=='-',c=getc();
    while(c>='0'&&c<='9') n=(n<<1)+(n<<3)+(c^48),c=getc();
    n=neg?-n:n;
}
void print(int x){
    if(!x) return putchar('0'),void();
    if(x<0) putchar('-'),x=-x;
    int top=0,a[20];
    while(x) a[top++]=x%10,x/=10;
    while(top) putchar(a[--top]+'0');
}
void dfs(int x,int fafa){
    a[f[x]=++len]=x,dep[x]=dep[fafa]+1;
    for(auto p:s[x]){
        if(p==fafa) continue;
        fa[p][0]=x,dfs(p,x);
    }
    a[g[x]=++len]=x;
}
int LCA(int x,int y){
    if(dep[x]<dep[y]) swap(x,y);
    if(dep[x]!=dep[y])
        for(int i=20;i>=0;i--){
            int v=fa[x][i];
            if(dep[v]>=dep[y]) x=v;
        }
    if(x==y) return x;
    for(int i=20;i>=0;i--){
        int vx=fa[x][i],vy=fa[y][i];
        if(vx!=vy) x=vx,y=vy;
    }
    return fa[x][0];
}
void sol(int x){
    if(vis[x]) cnt1[h[x]/block_size]--,cnt2[h[x]]--;
    else cnt1[h[x]/block_size]++,cnt2[h[x]]++;
    vis[x]=!vis[x];
}
bool cmp(query x,query y){
    if(x.l/B^y.l/B) return x.l<y.l;
    if(x.r/B^y.r/B) return (x.l/B&1)?x.r<y.r:x.r>y.r;
    return x.t<y.t;
}
int main(){
    read(n),read(q);
    for(int i=1;i<=n;i++) read(h[i]),c[++ccnt]=h[i];
    for(int i=1,a,b;i<n;i++){
        read(a),read(b);
        s[a].push_back(b);
        s[b].push_back(a);
    }
    dfs(1,0);
    for(int j=1;j<=20;j++)
        for(int i=1;i<=n;i++)
            fa[i][j]=fa[fa[i][j-1]][j-1];
    for(int i=1,k,x,y;i<=q;i++){
        read(k),read(x),read(y);
        if(!k) q2[++rcnt]={x,y},c[++ccnt]=y;
        else{
            if(f[x]>f[y]) swap(x,y);
            q1[++qcnt]={k,LCA(x,y)==x?f[x]:g[x],f[y],rcnt,qcnt};
        }
    }
    sort(c+1,c+ccnt+1);
    ccnt=unique(c+1,c+ccnt+1)-c-1;
    B=ceil(pow(len,2.0/3));
    block_size=ceil(sqrt(ccnt));
    for(int i=1;i<=n;i++) h[i]=lower_bound(c+1,c+ccnt+1,h[i])-c;
    for(int i=1;i<=rcnt;i++) q2[i].c=lower_bound(c+1,c+ccnt+1,q2[i].c)-c;
    int lenb=(ccnt-1)/block_size+1;
    sort(q1+1,q1+qcnt+1,cmp);
    for(int i=1,l=1,r=0,t=0;i<=qcnt;i++){
        auto p=q1[i];
        while(l>p.l) sol(a[--l]);
        while(r<p.r) sol(a[++r]);
        while(l<p.l) sol(a[l++]);
        while(r>p.r) sol(a[r--]);
        while(t<p.t){
            t++;
            int u=q2[t].p;
            if(!vis[u]) swap(h[u],q2[t].c);
            else sol(u),swap(h[u],q2[t].c),sol(u); 
        }
        while(t>p.t){
            int u=q2[t].p;
            if(!vis[u]) swap(h[u],q2[t].c);
            else sol(u),swap(h[u],q2[t].c),sol(u); 
            t--;
        }
        int u=a[l],v=a[r],lca=LCA(u,v);
        if(u!=lca&&v!=lca) sol(lca);
        int k=p.k;
        for(int i=lenb-1;i>=0;i--){
            if(k>cnt1[i]) k-=cnt1[i];
            else{
                for(int j=(i+1)*block_size-1;j>=i*block_size;j--){
                    if(j>ccnt) continue;
                    if(cnt2[j]){
                        if(k<=cnt2[j]){ans[p.id]=j;break;}
                        k-=cnt2[j];
                    }
                }
                break;
            }
        }
        if(u!=lca&&v!=lca) sol(lca);
    }
    for(int i=1;i<=qcnt;i++){
        if(!ans[i]) puts("invalid request!");
        else print(c[ans[i]]),puts("");
    }
    return 0;
}
2025/8/1 21:08
加载中...