RE 0pts求调
查看原帖
RE 0pts求调
623818
lose_moment楼主2025/7/30 17:56
#include <bits/stdc++.h>
#define lowbit(x) (x&(-x))
#define TSIZE(x) ((n>>(dep[x]-1))+5)
using namespace std;
typedef long long LL;
inline int read()
{
	int x=0,f=1;char ch=getchar();
	while (ch<'0'||ch>'9'){if (ch=='-') f=-1;ch=getchar();}
	while (ch>='0'&&ch<='9'){x=(x<<1)+(x<<3)+ch-48;ch=getchar();}
	return x*f;
}
const int N=1e5+5,INF=0x3f3f3f3f,D=log2(N);
struct Edge{
	int to,nxt;
}e[N<<1];
int m,n,last_ans,value[N],head[N],cnt;
int rt,RT,mirt=INF,Size,size[N],father[N],dis[N][D],dep[N];//disΪiµãÔÚj²ãµã·ÖÊ÷µÄµ½ÖØÐĵľàÀ룻 
bool cut[N];
vector<int> sum[2][N];//Ê÷×´Êý×飬ÿ¸ö×ÓÊ÷¿ªÒ»¸ö ¹²nlogn; sum0µ½ÖØÐÄ£¬sum1µ½fa£» 
inline int qrysum(int x,int y,int id)
{
	int res=0;
	if(y>TSIZE(x)) y=TSIZE(x)-3;
	while(y>0)
	{
		res+=sum[id][x][lowbit(y)];
		y-=lowbit(y);
	}
	return res+sum[id][x][0];
}
//sum[x] +k;
inline void changesum (int x,int y,int k,int id)
{
	if(!y) {
		sum[id][x][0]+=k;
		return;
	}
	int lim=TSIZE(x)-3;
	while(y<lim&&y>0) {
		sum[id][x][y]+=k;
		y+=lowbit(y);
	}
}

inline void add_edge(int u,int v) {e[++cnt].nxt=head[u],e[cnt].to=v; head[u]=cnt;}
// mirt=INF; update Size
void getrt(int fa,int u,int id)
{
	size[u]=1; dis[u][id]=dis[fa][id]+1;
	int temp=0;
	for(int i=head[u];i;i=e[i].nxt) {
		int v=e[i].to;
		if(v==fa||cut[v]) continue;
		getrt(u,v,id); size[u]+=size[v];
		temp=max(temp,size[v]);
	}
	temp=max(temp,Size-size[u]);
	if(temp<mirt) {
		rt=u; mirt=temp;
	}
}
void getsize(int fa,int u)
{
	size[u]=1;
	for(int i=head[u];i;i=e[i].nxt) {
		int v=e[i].to;
		if(v==fa||cut[v]==1) continue;
		getsize(u,v);
		size[u]+=size[v];
	}
}
void build(int fa,int u,int depth)//depΪµã·ÖÊ÷µÄ²ãÊý 
{
	cut[u]=1; dep[u]=depth;
	getsize(fa,u);
	for(int i=head[u];i;i=e[i].nxt) {
		int v=e[i].to;
		if(cut[v]||v==fa) continue;
		mirt=INF; Size=size[v]; getrt(u,v,depth);
		father[rt]=u;
		build(u,rt,depth+1);
	}
}
//ÔÚµã·ÖÊ÷ÉÏ·ÖÁ½À࣬¹ýÖØÐĺͷÖÖÎ ***×¢Òâ´ÓÏÂÏòÉÏÕҺ͸üР
inline int query(int x,int k)
{
	int res=0;
	for(int i=x;i;i=father[i]) {
		if(k-dis[x][dep[i]]>=0) res+=qrysum(i,k-dis[x][dep[i]],0);
		if(!father[i]) continue;
		if(k-dis[x][dep[father[i]]]>=0) res-=qrysum(i,k-dis[x][dep[father[i]]],1);
	}
	return res;
}
inline void change(int x,int y)
{
	int d=y-value[x]; value[x]=y;
	for(int i=x;i;i=father[i])
	{
		changesum(i,dis[x][dep[i]],d,0);
		if(father[i]) changesum(i,dis[x][dep[father[i]]],d,1);
	}
}
inline void init()
{
	for(int i=1;i<=n;i++) {
		int j=0;
		while(++j <=TSIZE(i)) {
			sum[0][i].push_back(0);
			sum[1][i].push_back(0);
		}
	}
	for(int i=1;i<=n;i++) {
		for(int j=i;j;j=father[j]) {
			changesum(j,dis[i][dep[j]],value[i],0);
			if(father[i]) changesum(j,dis[i][dep[father[j]]],value[i],1);
		}
	}
}
int main()
{
    n=read(); m=read();
    for(int i=1;i<=n;i++) value[i]=read();
    for(int i=1;i<n;i++) {
    	int u=read(),v=read();
    	add_edge(u,v); add_edge(v,u);
	}
	Size=n; getrt(0,1,0); RT=rt; build(0,rt,1);
	init();//¶Ôsum³õʼ»¯
    while(m--) {
    	int opt=read(),x=read(),y=read();
    	x^=last_ans; y^=last_ans;
    	if(opt) {
    		change(x,y);
    		continue;
		}
		last_ans=query(x,y);
		printf("%d\n",last_ans);
	}
    return 0;
}
2025/7/30 17:56
加载中...