(这题里根节点应该是没有给定的罢)
以 1 为根节点,QMAX 的结果全部正确,QSUM 有问题
以 2 为根节点,QMAX 和 QSUM 的结果都有问题
所以由此看来两个都有问题?
#include<bits/stdc++.h>
using namespace std;
typedef long long LL;
const int maxn=30004;
char op[14],res[maxn*10];
int n,m,u,v,x,y,z,tot,a[maxn],w[maxn];
inline void reads(char *s){
char c=getchar();int cnt=0;
for(;c<'A'||c>'Z';c=getchar());
for(;c>='A'&&c<='Z';c=getchar())
s[cnt++]=c;
}
inline void read(int &x){
bool f=0;char c=getchar();x=0;
for(;c<'0'||c>'9';c=getchar());
for(;c>='0'&&c<='9';c=getchar())
x=x*10+(c^48);
}
void save(const LL x){
if(x>9)
save(x/10);
res[++tot]=x%10+48;
}
inline void _swap(int &a,int &b){ a^=b;b=a^b;a^=b;}
inline const int _max(const int &a,const int &b){
return a>b?a:b;
}
namespace gragh{
int cnt,head[maxn],to[maxn<<1],nxt[maxn<<1];
inline void add_edge(int a,int b){
++cnt;
nxt[cnt]=head[a];
to[cnt]=b;
head[a]=cnt;
}
}
namespace segt{
LL s[maxn<<2],maxi[maxn<<2];
void assign(int l,int r,int node,int p,int v){
if(l==r){
s[node]=maxi[node]=v;
return ;
}
int mid=(l+r)>>1,lnode=node<<1,rnode=node<<1|1;
if(p<=mid)
assign(l,mid,lnode,p,v);
else
assign(mid+1,r,rnode,p,v);
s[node]=s[lnode]+s[rnode];
maxi[node]=_max(maxi[lnode],maxi[rnode]);
}
LL sum(int l,int r,int node,int start,int end){
if(start<=l&&r<=end)
return s[node];
int mid=(l+r)>>1,lnode=node<<1,rnode=node<<1|1;
LL ans=0;
if(start<=mid)
ans+=sum(l,mid,lnode,start,end);
if(end>mid)
ans+=sum(mid+1,r,rnode,start,end);
return ans;
}
LL max(int l,int r,int node,int start,int end){
if(start<=l&&r<=end)
return maxi[node];
int mid=(l+r)>>1,lnode=node<<1,rnode=node<<1|1;
LL ans=0;
if(start<=mid)
ans=max(l,mid,lnode,start,end);
if(end>mid)
ans=_max(ans,max(mid+1,r,rnode,start,end));
return ans;
}
}
namespace chains{
int cnt,d[maxn],f[maxn],t[maxn],treesz[maxn],hson[maxn],ord[maxn];
void dfs1(int node,int fa,int dep){
d[node]=dep;
f[node]=fa;
treesz[node]=1;
int MAX=-1;
for(int i=gragh::head[node];i;i=gragh::nxt[i]){
int to=gragh::to[i];
if(to!=fa){
dfs1(to,node,dep+1);
int ssz=treesz[to];
treesz[node]+=ssz;
if(MAX<ssz){
MAX=ssz;
hson[node]=to;
}
}
}
}
void dfs2(int node,int top){
ord[node]=++cnt;
w[cnt]=a[node];
t[node]=top;
if(!hson[node])
return ;
dfs2(hson[node],top);
for(int i=gragh::head[node];i;i=gragh::nxt[i]){
int to=gragh::to[i];
if(ord[to]==0)
dfs2(to,to);
}
}
inline int chain_sum(int a,int b){
int ans=0;
while(t[a]!=t[b]){
if(d[t[a]]<d[t[b]])
_swap(a,b);
ans+=segt::sum(1,n,1,ord[t[a]],ord[a]);
a=f[t[a]];
}
if(d[a]>d[b])
_swap(a,b);
ans+=segt::sum(1,n,1,ord[a],ord[b]);
return ans;
}
inline LL chain_max(int a,int b){
LL ans=-0x7fffffff;
while(t[a]!=t[b]){
if(d[t[a]]<d[t[b]])
_swap(a,b);
ans=_max(ans,segt::max(1,n,1,ord[t[a]],a));
a=f[t[a]];
}
if(d[a]>d[b])
_swap(a,b);
ans=_max(ans,segt::max(1,n,1,ord[a],ord[b]));
return ans;
}
}
signed main(){
read(n);
for(int i=1;i<n;i++){
read(u),read(v);
gragh::add_edge(u,v);
gragh::add_edge(v,u);
}
for(int i=1;i<=n;i++)
read(a[i]);
chains::dfs1(1,0,1);
chains::dfs2(1,1);
for(int i=1;i<=n;i++)
segt::assign(1,n,1,i,w[i]);
read(m);
while(m--){
reads(op);read(x),read(y);
if(op[0]=='C')
segt::assign(1,n,1,chains::ord[x],y);
else{
if(op[1]='M')
save(chains::chain_max(x,y));
else
save(chains::chain_sum(x,y));
res[++tot]='\n';
}
}
fwrite(res+1,1,tot,stdout);
return 0;
}