AFO

模板

注意事项:

  • 需要的数组:1.建图(ver,nex,head).  2,维护链的数据结构:线段树/树状数组.  3.树剖:dfn,wson,top,size,deep

  • dfn[1]=fa[1]=1;
  • gai(dfn[x])
  • dfs1记录字数大小size/深度d/父节点fa/重儿子wson
  • dfs1记录dfn,pre,链顶top

 

#include<iostream>
#include<stdio.h>

using namespace std;

int g,q,h,i,m,n,j,k,a[100001],nex[100001],head[100001],ver[100001],cnt;
int wson[100005],top[100005],dfn[100001],d[100001],fa[100001],size[100001];
int pre[100005],sum[400010],smm[400011];
char c[10001];

void add(int x,int y)
{
	cnt+=1;
	ver[cnt]=y;
	nex[cnt]=head[x];
	head[x]=cnt;
}

void update(int now)
{
	sum[now]=sum[now*2]+sum[now*2+1];
	smm[now]=max(smm[now*2],smm[now*2+1]);
}

void built(int now,int l,int r)
{
	if(l==r) sum[now]=smm[now]=a[pre[l]];
	else
	{
		int mid=(l+r)/2;
		built(now*2,l,mid);
		built(now*2+1,mid+1,r);
		update(now);
	}
}

void dfs1(int x,int y)
{
	size[x]=1;
	for(int i=head[x];i;i=nex[i])
	{
		int t=ver[i];
		if(t==y) continue;
		fa[t]=x;
		d[t]=d[x]+1;
		dfs1(t,x);
		if(size[t]>size[wson[x]]) wson[x]=t;
		size[x]+=size[t];
	}
}

void dfs2(int x,int y)
{
	cnt+=1;
	dfn[x]=cnt; pre[cnt]=x; top[x]=y;
	if(wson[x]) dfs2(wson[x],y);
	for(int i=head[x];i;i=nex[i])
	{
		int t=ver[i];
		if(t==fa[x] || t==wson[x]) continue;
		dfs2(t,t);
	}
}

int qsum(int now,int l,int r,int ll,int rr)
{
	if((l>=ll)&&(r<=rr)) return sum[now];
	int mid=(l+r)/2,ans=0;
	if(ll<=mid) ans+=qsum(now*2,l,mid,ll,rr);
	if(rr>mid) ans+=qsum(now*2+1,mid+1,r,ll,rr);
	return ans;
}

int qmax(int now,int l,int r,int ll,int rr)
{
	if((l>=ll)&&(r<=rr)) return smm[now];
	int mid=(l+r)/2,ans=-0x7ffffff;
	if(ll<=mid) ans=max(ans,qmax(now*2,l,mid,ll,rr));
	if(rr>mid) ans=max(ans,qmax(now*2+1,mid+1,r,ll,rr));
	return ans;
}

void gai(int now,int l,int r,int w,int z)
{
	if(l==r) sum[now]=smm[now]=z;
	else
	{
		int mid=(l+r)/2,ans=0;
		if(mid>=w) gai(now*2,l,mid,w,z);
		else gai(now*2+1,mid+1,r,w,z);
		update(now);
	}
}

int cham(int x,int y)
{
	int ans=-0x7fffffff;
	while(top[x]!=top[y])
	{
		if(d[top[x]]<d[top[y]]) swap(x,y);
		ans=max(qmax(1,1,n,dfn[top[x]],dfn[x]),ans);
		x=fa[top[x]];
	}
	if(d[x]<d[y]) swap(x,y);
	ans=max(ans,qmax(1,1,n,dfn[y],dfn[x]));
	return ans;
}

int chas(int x,int y)
{
	int ans=0;
	while(top[x]!=top[y])
	{
		if(d[top[x]]<d[top[y]]) swap(x,y);
		ans+=qsum(1,1,n,dfn[top[x]],dfn[x]);
		x=fa[top[x]];
	}
	if(d[x]<d[y]) swap(x,y);
	ans+=qsum(1,1,n,dfn[y],dfn[x]);
	return ans;
}

int main()
{
	scanf("%d",&n);
	for(i=1;i<n;i++) 
	{
		scanf("%d%d",&g,&h);
		add(g,h);
		add(h,g);
	}
	for(i=1;i<=n;i++) scanf("%d",&a[i]);
	scanf("%d",&q);
	d[1]=fa[1]=1; cnt=0;
	dfs1(1,0); dfs2(1,1); built(1,1,n);
	
	for(i=1;i<=q;i++)
	{
		scanf("%s%d%d",c,&g,&h);
		if(c[1]=='H') gai(1,1,n,dfn[g],h);
		if(c[1]=='M') printf("%d\n",cham(g,h));
		if(c[1]=='S') printf("%d\n",chas(g,h));
	}
}

  

posted @ 2018-07-09 19:53  ZUTTER☮  阅读(174)  评论(0编辑  收藏  举报