Section 4.5
parent
0050bc4d6a
commit
ada5c5b19d
@ -0,0 +1,135 @@
|
||||
#include <cstdio>
|
||||
#include <cctype>
|
||||
#define L(x) ((x) << 1)
|
||||
#define R(x) ((x) << 1 | 1)
|
||||
#define avg(x, y) (((x) + (y)) >> 1)
|
||||
inline int max(int a, int b) { return a > b ? a : b; }
|
||||
inline int min(int a, int b) { return a < b ? a : b; }
|
||||
template <typename T> inline void swap(T &a, T &b)
|
||||
{
|
||||
T t = a;
|
||||
a = b;
|
||||
b = t;
|
||||
}
|
||||
inline void read(int &x)
|
||||
{
|
||||
int ch = x = 0, sign = 1;
|
||||
while (!isdigit(ch = getchar())) if (ch == '-') sign = -1;
|
||||
for (; isdigit(ch); ch = getchar()) x = x * 10 + ch - '0';
|
||||
x *= sign;
|
||||
}
|
||||
const int N = int(3e4 + 5), inf = 0x3f3f3f3f;
|
||||
int adj[N], nxt[N << 1], to[N << 1], ecnt;
|
||||
int sum[N << 2], mx[N << 2];
|
||||
int n, sz[N], son[N], dep[N], fa[N], top[N], idx[N], pos[N], val[N];
|
||||
inline void addEdge(int f, int t)
|
||||
{
|
||||
ecnt++;
|
||||
nxt[ecnt] = adj[f];
|
||||
adj[f] = ecnt;
|
||||
to[ecnt] = t;
|
||||
}
|
||||
void build(int k, int l, int r)
|
||||
{
|
||||
if (l == r - 1) return void(sum[k] = mx[k] = val[idx[l]]);
|
||||
int m = avg(l, r);
|
||||
build(L(k), l, m);
|
||||
build(R(k), m, r);
|
||||
sum[k] = sum[L(k)] + sum[R(k)];
|
||||
mx[k] = max(mx[L(k)], mx[R(k)]);
|
||||
}
|
||||
void modify(int k, int l, int r, int p, int v)
|
||||
{
|
||||
if (l == r - 1) return void(sum[k] = mx[k] = v);
|
||||
int m = avg(l, r);
|
||||
(p < m) ? modify(L(k), l, m, p, v) : modify(R(k), m, r, p, v);
|
||||
sum[k] = sum[L(k)] + sum[R(k)];
|
||||
mx[k] = max(mx[L(k)], mx[R(k)]);
|
||||
}
|
||||
int qsum(int k, int l, int r, int x, int y)
|
||||
{
|
||||
if (x <= l && r <= y) return sum[k];
|
||||
int m = avg(l, r), res = 0;
|
||||
if (x < m) res += qsum(L(k), l, m, x, y);
|
||||
if (y > m) res += qsum(R(k), m, r, x, y);
|
||||
return res;
|
||||
}
|
||||
int qmax(int k, int l, int r, int x, int y)
|
||||
{
|
||||
if (x <= l && r <= y) return mx[k];
|
||||
int m = avg(l, r), res = -inf;
|
||||
if (x < m) res = max(res, qmax(L(k), l, m, x, y));
|
||||
if (y > m) res = max(res, qmax(R(k), m, r, x, y));
|
||||
return res;
|
||||
}
|
||||
int psum(int u, int v)
|
||||
{
|
||||
int res = 0;
|
||||
while (top[u] != top[v])
|
||||
{
|
||||
if (dep[top[u]] < dep[top[v]]) swap(u, v);
|
||||
res += qsum(1, 0, n, pos[top[u]], pos[u] + 1);
|
||||
u = fa[top[u]];
|
||||
}
|
||||
if (dep[u] > dep[v]) swap(u, v);
|
||||
return res + qsum(1, 0, n, pos[u], pos[v] + 1);
|
||||
}
|
||||
int pmax(int u, int v)
|
||||
{
|
||||
int res = -inf;
|
||||
while (top[u] != top[v])
|
||||
{
|
||||
if (dep[top[u]] < dep[top[v]]) swap(u, v);
|
||||
res = max(res, qmax(1, 0, n, pos[top[u]], pos[u] + 1));
|
||||
u = fa[top[u]];
|
||||
}
|
||||
if (dep[u] > dep[v]) swap(u, v);
|
||||
return max(res, qmax(1, 0, n, pos[u], pos[v] + 1));
|
||||
}
|
||||
void init()
|
||||
{
|
||||
static int que[N];
|
||||
int len = 0, u, v;
|
||||
que[len++] = 1;
|
||||
for (int i = 0; i < len; i++)
|
||||
{
|
||||
sz[u = que[i]] = 1;
|
||||
for (int e = adj[u]; e; e = nxt[e])
|
||||
if ((v = to[e]) != fa[u])
|
||||
fa[v] = u, dep[v] = dep[u] + 1, que[len++] = v;
|
||||
}
|
||||
for (int i = len - 1; i; i--)
|
||||
{
|
||||
u = que[i], v = fa[u];
|
||||
sz[v] += sz[u];
|
||||
if (sz[u] > sz[son[v]]) son[v] = u;
|
||||
}
|
||||
for (int i = 0, tot = 0; i < len; i++)
|
||||
if (top[u = que[i]] == 0)
|
||||
for (v = u; v; v = son[v])
|
||||
idx[pos[v] = tot++] = v, top[v] = u;
|
||||
}
|
||||
int main()
|
||||
{
|
||||
read(n);
|
||||
for (int i = 1, x, y; i < n; i++)
|
||||
{
|
||||
read(x), read(y);
|
||||
addEdge(x, y), addEdge(y, x);
|
||||
}
|
||||
for (int i = 1; i <= n; i++) read(val[i]);
|
||||
init();
|
||||
build(1, 0, n);
|
||||
int m, u, v;
|
||||
read(m);
|
||||
static char op[10];
|
||||
while (m--)
|
||||
{
|
||||
scanf("%s", op);
|
||||
read(u), read(v);
|
||||
if (op[1] == 'H') modify(1, 0, n, pos[u], v);
|
||||
if (op[1] == 'M') printf("%d\n", pmax(u, v));
|
||||
if (op[1] == 'S') printf("%d\n", psum(u, v));
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
@ -0,0 +1,135 @@
|
||||
#include <cstdio>
|
||||
#include <cctype>
|
||||
#define L(x) ((x) << 1)
|
||||
#define R(x) ((x) << 1 | 1)
|
||||
#define avg(x, y) (((x) + (y)) >> 1)
|
||||
inline int max(int a, int b) { return a > b ? a : b; }
|
||||
inline int min(int a, int b) { return a < b ? a : b; }
|
||||
template <typename T> inline void swap(T &a, T &b)
|
||||
{
|
||||
T t = a;
|
||||
a = b;
|
||||
b = t;
|
||||
}
|
||||
inline void read(int &x)
|
||||
{
|
||||
int ch = x = 0, sign = 1;
|
||||
while (!isdigit(ch = getchar())) if (ch == '-') sign = -1;
|
||||
for (; isdigit(ch); ch = getchar()) x = x * 10 + ch - '0';
|
||||
x *= sign;
|
||||
}
|
||||
const int N = int(3e4 + 5), inf = 0x3f3f3f3f;
|
||||
int adj[N], nxt[N << 1], to[N << 1], ecnt;
|
||||
int sum[N << 2], mx[N << 2];
|
||||
int n, sz[N], son[N], dep[N], fa[N], top[N], idx[N], pos[N], val[N];
|
||||
inline void addEdge(int f, int t)
|
||||
{
|
||||
ecnt++;
|
||||
nxt[ecnt] = adj[f];
|
||||
adj[f] = ecnt;
|
||||
to[ecnt] = t;
|
||||
}
|
||||
void build(int k, int l, int r)
|
||||
{
|
||||
if (l == r - 1) return void(sum[k] = mx[k] = val[idx[l]]);
|
||||
int m = avg(l, r);
|
||||
build(L(k), l, m);
|
||||
build(R(k), m, r);
|
||||
sum[k] = sum[L(k)] + sum[R(k)];
|
||||
mx[k] = max(mx[L(k)], mx[R(k)]);
|
||||
}
|
||||
void modify(int k, int l, int r, int p, int v)
|
||||
{
|
||||
if (l == r - 1) return void(sum[k] = mx[k] = v);
|
||||
int m = avg(l, r);
|
||||
(p < m) ? modify(L(k), l, m, p, v) : modify(R(k), m, r, p, v);
|
||||
sum[k] = sum[L(k)] + sum[R(k)];
|
||||
mx[k] = max(mx[L(k)], mx[R(k)]);
|
||||
}
|
||||
int qsum(int k, int l, int r, int x, int y)
|
||||
{
|
||||
if (x <= l && r <= y) return sum[k];
|
||||
int m = avg(l, r), res = 0;
|
||||
if (x < m) res += qsum(L(k), l, m, x, y);
|
||||
if (y > m) res += qsum(R(k), m, r, x, y);
|
||||
return res;
|
||||
}
|
||||
int qmax(int k, int l, int r, int x, int y)
|
||||
{
|
||||
if (x <= l && r <= y) return mx[k];
|
||||
int m = avg(l, r), res = -inf;
|
||||
if (x < m) res = max(res, qmax(L(k), l, m, x, y));
|
||||
if (y > m) res = max(res, qmax(R(k), m, r, x, y));
|
||||
return res;
|
||||
}
|
||||
int psum(int u, int v)
|
||||
{
|
||||
int res = 0;
|
||||
while (top[u] != top[v])
|
||||
{
|
||||
if (dep[top[u]] < dep[top[v]]) swap(u, v);
|
||||
res += qsum(1, 0, n, pos[top[u]], pos[u] + 1);
|
||||
u = fa[top[u]];
|
||||
}
|
||||
if (dep[u] > dep[v]) swap(u, v);
|
||||
return res + qsum(1, 0, n, pos[u], pos[v] + 1);
|
||||
}
|
||||
int pmax(int u, int v)
|
||||
{
|
||||
int res = -inf;
|
||||
while (top[u] != top[v])
|
||||
{
|
||||
if (dep[top[u]] < dep[top[v]]) swap(u, v);
|
||||
res = max(res, qmax(1, 0, n, pos[top[u]], pos[u] + 1));
|
||||
u = fa[top[u]];
|
||||
}
|
||||
if (dep[u] > dep[v]) swap(u, v);
|
||||
return max(res, qmax(1, 0, n, pos[u], pos[v] + 1));
|
||||
}
|
||||
void init()
|
||||
{
|
||||
static int que[N];
|
||||
int len = 0, u, v;
|
||||
que[len++] = 1;
|
||||
for (int i = 0; i < len; i++)
|
||||
{
|
||||
sz[u = que[i]] = 1;
|
||||
for (int e = adj[u]; e; e = nxt[e])
|
||||
if ((v = to[e]) != fa[u])
|
||||
fa[v] = u, dep[v] = dep[u] + 1, que[len++] = v;
|
||||
}
|
||||
for (int i = len - 1; i; i--)
|
||||
{
|
||||
u = que[i], v = fa[u];
|
||||
sz[v] += sz[u];
|
||||
if (sz[u] > sz[son[v]]) son[v] = u;
|
||||
}
|
||||
for (int i = 0, tot = 0; i < len; i++)
|
||||
if (top[u = que[i]] == 0)
|
||||
for (v = u; v; v = son[v])
|
||||
idx[pos[v] = tot++] = v, top[v] = u;
|
||||
}
|
||||
int main()
|
||||
{
|
||||
read(n);
|
||||
for (int i = 1, x, y; i < n; i++)
|
||||
{
|
||||
read(x), read(y);
|
||||
addEdge(x, y), addEdge(y, x);
|
||||
}
|
||||
for (int i = 1; i <= n; i++) read(val[i]);
|
||||
init();
|
||||
build(1, 0, n);
|
||||
int m, u, v;
|
||||
read(m);
|
||||
static char op[10];
|
||||
while (m--)
|
||||
{
|
||||
scanf("%s", op);
|
||||
read(u), read(v);
|
||||
if (op[1] == 'H') modify(1, 0, n, pos[u], v);
|
||||
if (op[1] == 'M') printf("%d\n", pmax(u, v));
|
||||
if (op[1] == 'S') printf("%d\n", psum(u, v));
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
Binary file not shown.
Loading…
Reference in new issue