社区讨论

我这是不是爆栈了。。。

P2486[SDOI2011] 染色参与者 2已保存回复 1

讨论操作

快速查看讨论及其快照的属性,并进行相关操作。

当前回复
1 条
当前快照
1 份
快照标识符
@mi6le8wl
此快照首次捕获于
2025/11/20 06:47
4 个月前
此快照最后确认于
2025/11/20 06:47
4 个月前
查看原帖
rt,一直是RE,是不是我方法有问题还是爆栈了。。。
CPP
#include<iostream>
#include<cstdio>
#include<cstring>
#include<algorithm>
#include<ctype.h>
using namespace std;
#define read Read
#define add Add
#define to To
#define next Next
void swap(int &a,int &b){a=a^b;b=a^b;a=a^b;}
int read(){
    int x=0,f=1;char c=getchar();
    while(!isdigit(c)){if(c=='-')f=-1;c=getchar();}
    while(isdigit(c)){x=(x<<3)+(x<<1)+c-48;c=getchar();}
    return x*f;
}
const int maxn=200010;
int tot=0,son[maxn],dep[maxn],sz[maxn],f[maxn],p[maxn],top[maxn],to[maxn<<2],next[maxn<<2],head[maxn];
int L[maxn<<2],R[maxn<<2],tag[maxn<<2],sumv[maxn<<2],m,n,val[maxn],c[maxn];
void add(int x,int y){
    to[++tot]=y;
    next[tot]=head[x];
    head[x]=tot;
}
void dfs1(int u,int fa){
    f[u]=fa;dep[u]=dep[fa]+1;son[u]=-1;sz[u]=1;
    for(int i=head[u];i;i=next[i]){
        int v=to[i];
        if(v==fa)continue;
        dfs1(v,u);
        sz[u]+=sz[v];
        if(son[u]==-1||sz[son[u]]<sz[v])son[u]=v;
    }
}
int totp;
void dfs2(int u,int tp){
    p[u]=++totp;top[u]=tp;
    if(son[u]!=-1)dfs2(son[u],tp);
    for(int i=head[u];i;i=next[i]){
        int v=to[i];
        if(v!=f[u]&&v!=son[u])dfs2(v,v);
    }
}
#define ls o<<1,l,mid
#define rs o<<1|1,mid+1,r
void maintain(int o,int l,int r){
    if(tag[o]!=-1){
        L[o]=tag[o];R[o]=tag[o];sumv[o]=1;
    }
    else if(r>l){
        sumv[o]=sumv[o<<1]+sumv[o<<1|1];
        if(R[o<<1]==L[o<<1|1])sumv[o]--;
        L[o]=L[o<<1];R[o]=R[o<<1|1];
    }
}
void build(int o,int l,int r){
    tag[o]=-1;
    if(l==r){
        sumv[o]=1;L[o]=val[l];R[o]=val[l];
        return ;
    }
    int mid=(l+r)>>1;
    build(ls);build(rs);
    maintain(o,l,r);
}
void pushdown(int o){
    if(tag[o]!=-1){
        tag[o<<1]=tag[o];tag[o<<1|1]=tag[o];
        tag[o]=-1;
    }
}
void update(int o,int l,int r,int x,int y,int va){
    if(x<=l&&r<=y){
        tag[o]=va;
    }
    else {
        pushdown(o);
        int mid=(l+r)>>1;
        if(x<=mid)update(ls,x,y,va);else maintain(o<<1,l,mid);
        if(y>mid)update(rs,x,y,va);else maintain(o<<1|1,mid+1,r);
    }
    maintain(o,l,r);
}
int query_val(int o,int l,int r,int x,int y){
    if(tag[o]!=-1){
        return 1;
    }
    else if(x<=l&&r<=y){
        return sumv[o];
    }
    else {
        int res1=0,res2=0,mid=(l+r)>>1,cl=-2,cr=-1;
        if(x<=mid)res1=query_val(ls,x,y),cl=R[o<<1];
        if(y>mid)res2=query_val(rs,x,y),cr=L[o<<1|1];
        if(cl==cr)return res1+res2-1;
        else return res1+res2;
    }
}
int query_color(int o,int l,int r,int P){
    if(tag[o]!=-1)return tag[o];
    if(l==r){
        return L[o];
    }
    int mid=(l+r)>>1;
    if(P<=mid)query_color(ls,P);
    else query_color(rs,P);
}
void De(int o,int l,int r){
    printf("%d-%d L:%d R:%d sum:%d tag:%d\n",l,r,L[o],R[o],sumv[o],tag[o]);
    if(l==r)return ;
    if(tag[o]!=-1)return;
    int mid=(l+r)>>1;
    De(ls);De(rs);
}
void debug(){
    De(1,1,n);
}
int Find(int u,int v,int va,int pd){
    int f1=top[u],f2=top[v],ans=0;
    while(f1!=f2){
        if(dep[f1]<dep[f2]){
            swap(u,v);swap(f1,f2);
        }
        if(pd==0){
            ans+=query_val(1,1,n,p[f1],p[u]);
            int tmpr=query_color(1,1,n,p[f[f1]]),tmpl=query_color(1,1,n,p[f1]);
            if(tmpr==tmpl)ans--;
        }
        else {
            update(1,1,n,p[f1],p[u],va);
          //  debug();
        }
        u=f[f1];f1=top[u];
    }
    if(dep[u]<dep[v]){
        swap(u,v);
    }
    if(pd==0){
        ans+=query_val(1,1,n,p[v],p[u]);
        return ans==0?1:ans;
    }
    else {
        update(1,1,n,p[v],p[u],va);
      //  debug();
        return 0;
    }
}
int main(){
    tot=0;
    n=read();m=read();
    for(int i=1;i<=n;++i)c[i]=read();
    for(int i=1;i<n;++i){
        int x=read(),y=read();
        add(x,y);add(y,x);
    }
    dfs1(1,0);dfs2(1,1);
    for(int i=1;i<=n;++i){
       val[p[i]]=c[i];
    }
    build(1,1,n);
    //debug();
    char tmp;
    for(int i=1;i<=m;++i){
        scanf("%c",&tmp);int x=read(),y=read();
        if(tmp=='Q'){
            printf("%d\n",Find(x,y,0,0));
        }
        else {
            int z=read();
            Find(x,y,z,1);
        }
    }
    return 0;
}

回复

1 条回复,欢迎继续交流。

正在加载回复...