下载第一个测试点数据,发现竟然是样例----
#include <bits/stdc++.h>
using namespace std;
constexpr int N = 200010;
constexpr int inf = 1e9;
vector<int> adj[N];
int f[N][2],g[N][2],w[N];
int sz[N],dfn[N],dep[N],idx;
int a[N],fa[N],son[N],top[N],End[N];
struct Val{
int mat[2][2];
Val() {
mat[0][0] = mat[1][1] = 0;
mat[0][1] = mat[1][0] = -inf;
}
};
struct Info{
int l,r;Val s;
};
Val operator+(const Val &a,const Val &b){
Val c;
c.mat[0][0] = c.mat[1][1] = -inf;
for(int i = 0;i < 2;i ++ )
for(int j = 0;j < 2;j ++ )
for(int k = 0;k < 2;k ++ )
c.mat[i][j] = max(c.mat[i][j],a.mat[i][k] + b.mat[k][j]);
return c;
}
Info op(Info a){
int u = w[a.l];
a.s.mat[1][1] = -inf;
a.s.mat[1][0] = g[u][1];
a.s.mat[0][1] = a.s.mat[0][0] = g[u][0];
return a;
}
struct SegTree
{
int n;
vector<Info> tr;
SegTree(int n):n(n){
tr.resize(n * 4 + 1),build(1,1,n);
}
void build(int u,int l,int r){
tr[u].l = l,tr[u].r = r;
if(l != r){
int mid = (l + r) / 2;
build(u * 2,l,mid);
build(u * 2 + 1,mid + 1,r);
pushup(u);
} else {
tr[u].s.mat[1][1] = -inf;
tr[u].s.mat[1][0] = g[w[l]][1];
tr[u].s.mat[0][0] = tr[u].s.mat[0][1] = g[w[l]][0];
}
}
void modify(int u,int l,int r){
if(tr[u].l < l || tr[u].r > r){
int mid = (tr[u].l + tr[u].r) / 2;
if(l <= mid) modify(u * 2,l,r);
if(r > mid) modify(u * 2 + 1,l,r);
pushup(u);
}
else tr[u] = op(tr[u]);
}
Val ask(int u,int l,int r){
if(tr[u].l >= l && tr[u].r <= r)
return tr[u].s;
int mid = (tr[u].l + tr[u].r ) / 2;
Val ans;
if(l <= mid) ans = ask(u * 2,l,r);
if(r > mid) ans = ans + ask(u * 2 + 1,l,r);
return ans;
}
void pushup(int u){
tr[u].s = tr[u * 2].s + tr[u * 2 + 1].s;
}
};
void dfs1(int u,int v) {
fa[u] = v,sz[u] = 1;
f[u][1] = a[u];
for(auto x : adj[u]) {
if(x == v) continue;
dfs1(x,u);sz[u] += sz[x];
if(sz[son[u]] < sz[x])
son[u] = x;
f[u][1] += f[x][0];
f[u][0] += max(f[x][0],f[x][1]);
}
}
void dfs2(int u,int v) {
dfn[u] = ++ idx,top[u] = v;
g[u][1] = a[u];
if(!son[u]) {
End[u] = u;
return;
}
dfs2(son[u],v);
End[u] = End[son[u]];
for(auto x : adj[u]) {
if(x != son[u] && x != fa[u]) {
dfs2(x,x);
g[u][0] += max(f[x][1],f[x][0]);
g[u][1] += f[x][0];
}
}
}
int main() {
int n,m;cin >> n >> m;
for(int i = 1;i <= n;i ++ ) scanf("%d",a + i);
for(int i = 0;i < n - 1;i ++ ) {
int u,v;scanf("%d%d",&u,&v);
adj[u].push_back(v);
adj[v].push_back(u);
}
dfs1(1,0),dfs2(1,1);
for(int i = 1;i <= n;i ++ )
w[dfn[i]] = i;
SegTree segtree(n);
function<void(int,int)> update = [&](int u,int x) {
g[u][1] += x - a[u];
a[u] = x;
while(u) {
auto lst = segtree.ask(1,dfn[top[u]],dfn[End[u]]);
segtree.modify(1,dfn[u],dfn[u]);
auto now = segtree.ask(1,dfn[top[u]],dfn[End[u]]);
u = fa[top[u]];
g[u][0] += max(now.mat[0][0],now.mat[1][0]) - max(lst.mat[0][0],lst.mat[1][0]);
g[u][1] += now.mat[0][0] - lst.mat[0][0];
}
};
while(m -- ) {
int p,x;scanf("%d%d",&p,&x);
update(p,x);
auto ans = segtree.ask(1,1,dfn[End[1]]).mat;
printf("%d\n",max(ans[0][0],ans[1][0]));
}
}