求助上面28分,下面RE
查看原帖
求助上面28分,下面RE
563069
UQAQU楼主2024/8/1 22:40
#include<bits/stdc++.h>
#define ll long long int 
using namespace std;
const ll N=5000007;
ll n,m,r,mod;
struct tree{
	ll next,to,w;
}edge[2*N];
ll head[N],top[N],father[N],son[N],cnt;
ll val[N],num[N],id[N],size[N],deep[N],number;
ll d[4*N],lazy[N*4];
inline ll read(){
	ll ans=0,res=1;
	char c;
	while (c<'0' || c>'9'){
		if (c=='-'){
			res=-1;
		}
		c=getchar();
	}
	while (c>='0' && c<='9'){
		ans=(ans<<3)+(ans<<1)+(c^48);
		c=getchar();
	}
	return ans*res;
}
void add_edge(ll u,ll v){
	cnt++,edge[cnt].to=v,edge[cnt].next=head[u],head[u]=cnt;
}
void dfs1(ll u,ll v){
	deep[u]=deep[v]+1;
	father[u]=v;
	size[u]=1;
	for (ll i=head[u];i!=0;i=edge[i].next){
		ll j=edge[i].to;
		if (j==v){
			continue;
		}
		dfs1(j,u);
		size[u]+=size[j];
		if (size[j]>size[son[u]]){
			son[u]=j;
		}
	}
}
void dfs2(ll u,ll tp){
	number++;
	id[u]=number;
	val[number]=u;
	top[u]=tp;
	if (!son[u]){
		return ;
	}
	dfs2(son[u],tp);
	for (ll i=head[u];i!=0;i=edge[i].next){
		ll j=edge[i].to;
		if (j==son[u] || j==father[u]){
			continue;
		}
		dfs2(j,j);
	}
}
void build(ll l,ll r,ll p){
	if (l==r){
		d[p]=num[val[l]];
		return ;
	}
	ll mid=l+((r-l)>>1);
	build(l,mid,2*p),build(mid+1,r,2*p+1);
	d[p]+=d[2*p]+d[p*2+1];
	d[p]%=mod;
	return ;
}
ll query(ll l,ll r,ll s,ll t,ll p){
	if (l<=s && t<=r){
		return d[p]%mod;
	}
	if (s>r || t<l){
		return 0;
	}
	ll mid=s+((t-s)>>1);
	if (lazy[p]!=0){
		d[p*2]+=lazy[p]*(mid-s+1),d[p*2+1]+=lazy[p]*(t-mid);
		d[p*2]%=mod,d[p*2+1]%=mod;
		lazy[p*2]+=lazy[p],lazy[p*2+1]+=lazy[p],lazy[2*p]%=mod,lazy[2*p+1]%=mod;
		lazy[p]=0;
	}
	ll ans=0;
	if (l<=mid){
		ans+=query(l,r,s,mid,p*2);
		ans%=mod;
	}
	if (r>mid){
		ans+=query(l,r,mid+1,t,2*p+1);
		ans%=mod;
	}
	return ans%=mod;
}
ll query_sum(ll u,ll v){
	ll res=0;
	while(top[u]!=top[v]){
		if (deep[top[u]]<deep[top[v]]){
			swap(u,v);
		}
		res+=query(id[top[u]],id[u],1,number,1);
		u=father[top[u]];
		res%=mod;
	}
	if (deep[u]<deep[v]){
		swap(u,v);
	} 
	res+=query(id[v],id[u],1,number,1);
	res%=mod;
	return res%mod;
}
ll query_tree(ll u){
	return query(id[u],id[u]+size[u]-1,1,number,1);
}
void update(ll l,ll r,ll s,ll t,ll k,ll p){
	if (l<=s && t<=r){
		d[p]+=(t-s+1)*k,lazy[p]+=k;
		d[p]%=mod;
		lazy[p]%=mod;
		return ;
	}
	if (s>r || t<l){
		return ;
	}
	ll mid=s+((t-s)>>1);
	if (lazy[p]!=0 && s!=t){
		d[2*p]+=lazy[p]*(mid-s+1),d[p*2+1]+=lazy[p]*(t-mid);
		d[p*2]%=mod,d[p*2+1]%=mod;
		lazy[p*2]+=lazy[p],lazy[p*2+1]+=lazy[p];
		lazy[p*2]%=mod,lazy[p*2+1]%=mod;
		lazy[p]=0;
	}
	if (l<=mid){
		update(l,r,s,mid,k,2*p);
	}
	if (r>mid){
		update(l,r,mid+1,t,k,2*p+1);
	}
	d[p]=d[p*2]+d[p*2+1];
	d[p]%=mod;
}
void update_path(ll u,ll v,ll k){
	while(top[u]!=top[v]){
		if (deep[u]<deep[v]){
			swap(u,v);
		}
		update(id[top[u]],id[u],1,number,k,1);
		u=father[top[u]];
	}
	if (deep[u]<deep[v]){
		swap(u,v);
	}
	update(id[v],id[u],1,number,k,1);
}
void update_tree(ll u,ll k){
	update(id[u],id[u]+size[u]-1,1,number,k,1);
}
int main()
{
	n=read(),m=read(),r=read(),mod=read();
	for (ll i=1;i<=n;i++){
		num[i]=read();
		num[i]%=mod;
	}
	for (ll i=1;i<=n-1;i++){
		ll x,y;
		x=read(),y=read();
		add_edge(x,y);
		add_edge(y,x);
	}
	dfs1(r,0);
	dfs2(r,r);
	build(1,n,1);
	while (m--){
		ll t,x,y,z;
		t=read();
		if (t==1){
			x=read(),y=read(),z=read();
			update_path(x,y,z);
		}
		if (t==2){
			x=read(),y=read();
			cout<<query_sum(x,y)%mod<<endl;
		}
		if (t==3){
			x=read(),z=read();
			update_tree(x,z);
		}
		if (t==4){
			x=read();
			cout<<query_tree(x)%mod<<endl;
		}
	}
	return 0;
}


#include<bits/stdc++.h>
#define ll long long int
const int N=5e6+7;
using namespace std;
struct tree{
    int to,next,w;
}edge[2*N];
int n,m,r,mod;
int head[N],cnt,deep[N],sum[N],ch[N];
int top[N],fa[N],son[N],number,size[N],val[N],lazy[N],id[N];
void add_edge(int u,int v){
    cnt++;
    edge[cnt].to=v,edge[cnt].next=head[u],head[u]=cnt;
}
void dfs1(int u,int v){
    deep[u]=deep[v]+1;
    fa[u]=v;
    size[u]=1;
    for (int i=head[u];i!=0;i=edge[i].next){
        int j=edge[i].to;
        if (j==v){
            continue;
        }
        dfs1(j,u);
        size[u]+=size[j];
        if (size[j]>size[son[u]]){
            son[u]=j;
        }
    }
}
void dfs2(int u,int v){
    number++;
    id[u]=number,val[number]=u,top[u]=v;
    if (!son[u]){
        return ;
    }
    dfs2(son[u],v);
    for (int i=head[u];i!=0;i=edge[i].next){
        int j=edge[i].to;
        if (j!=fa[u] && j!=son[u]){
            dfs2(j,j);
        }
    }
    return ;
}
void build(int u,int l,int r){
    if (l==r){
        sum[u]=ch[val[l]];
        return ;
    }
    int mid=(l+r)>>1;
    build(2*u,l,mid);
    build(2*u+1,mid+1,r);
    sum[u]+=sum[2*u]+sum[2*u+1];
    sum[u]%=mod;
    return ;
}
void push(int u,int l,int r){
    int mid=(l+r)>>1;
    lazy[2*u]+=lazy[u];lazy[2*u]%=mod;
    lazy[2*u+1]+=lazy[u];lazy[2*u+1]%=mod;
    sum[2*u]+=lazy[u]*(mid-l+1);sum[2*u]%=mod;
    sum[2*u+1]+=lazy[u]*(r-mid);sum[2*u]%=mod;
    lazy[u]=0;
    return ;
}
void update(int u,int s,int t,int l,int r,int k){
    if (l<=s && r>=t){
        sum[u]+=k*(t-s+1);sum[u]%=mod;
        lazy[u]+=k;lazy[u]%=mod;
        return ;
    }
    if(s>r||t<l)return ;
    int mid=(s+t)>>1;
    if (lazy[u]!=0){
        push(u,s,t);
    }
    if (l>=mid){
        update(2*u,s,mid,l,r,k);
    }
    if (r>mid){
        update(2*u+1,mid+1,t,l,r,k);
    }
    sum[u]=(sum[2*u]+sum[2*u+1])%mod;
    return ;
}
ll query(int u,int s,int t,int l,int r){
    if (l<=s && r>=t){
        return sum[u]%=mod;
    }
    if(s>r|| t<l) return 0;
    int mid=(s+t)>>1;
    ll ans=0;
    if (mid>=l){
        ans+=query(2*u,s,mid,l,r);
        ans%=mod;
    }
    if (r>mid){
        ans+=query(2*u+1,mid+1,t,l,r);
        ans%=mod;
    }
    return ans%=mod;
}
ll query_sum(int u,int v){
    ll ans=0;
    while (top[u]!=top[v]){
        if (deep[top[u]]<deep[top[v]]){
            swap(u,v);
        }
        ans+=query(1,1,number,id[top[u]],id[u]);
        u=fa[top[u]];
    }
    if (id[u]<id[v]){
        swap(u,v);
    }
    ans+=query(1,1,number,id[v],id[u]);
    return ans;
}
void update_path(int u,int v,int k){
    while (top[u]!=top[v]){
        if (deep[u]<deep[v]){
            swap(u,v);
        }
        update(1,1,number,id[top[u]],id[u],k);
        u=fa[top[u]];
    }
    if (id[u]<id[v]){
        swap(u,v);
    }
    update(1,1,number,id[v],id[u],k);
}
int main()
{
    int n,m,r,mod;
    cin>>n>>m>>r>>mod;
    for (int i=1;i<=n;i++){
        cin>>ch[i];
    }
    for (int i=1;i<=n-1;i++){
        int x,y;
        cin>>x>>y;
        add_edge(x,y),add_edge(y,x);
    }
    dfs1(r,0);
    dfs2(r,r);
    build(1,1,n);
    while (m--){
        int t,x,y,z;
        cin>>t;
        if (t==1){
            cin>>x>>y>>z;
            update_path(x,y,z%mod);
        }
        if (t==2){
            cin>>x>>y;
            cout<<query_sum(x,y)%mod<<endl;
        }
        if (t==3){
            cin>>x>>y;
            update(1,1,n,id[x],id[x]+size[x]-1,y%mod);
        }
        if (t==4){
            cin>>x;
            cout<<query(1,1,n,id[x],size[x]+id[x]-1)%mod<<endl;
        }
    }
    return 0;
}
2024/8/1 22:40
加载中...