#include #define rep(i, n) for (int i = 0; i < (n); i++) #define repr(i, n) for (int i = (n) - 1; i >= 0; i--) #define rep2(i, l, r) for (int i = (l); i < (r); i++) #define rep2r(i, l, r) for (int i = (r) - 1; i >= (l); i--) #define range(a) a.begin(), a.end() using namespace std; using ll = long long; template struct lazy_segtree { int N; vector vec; vector mat; Vec vec_ident; Mat mat_ident; function vec_vec; function mat_vec; function mat_mat; lazy_segtree( int n, function init, Vec vec_ident_, Mat mat_ident_, function vec_vec_, function mat_vec_, function mat_mat_) : vec_ident(vec_ident_), mat_ident(mat_ident_), vec_vec(vec_vec_), mat_vec(mat_vec_), mat_mat(mat_mat_) { N = 1; while (N < n) N *= 2; vec.resize(N * 2, vec_ident); mat.resize(N * 2, mat_ident); for (int i = 0; i < n; i++) { vec[i + N] = init(i); } for (int i = N - 1; i >= 1; i--) { pull(i); } } void apply(int k, Mat v) { mat[k] = mat_mat(v, mat[k]); vec[k] = mat_vec(v, vec[k]); } void push(int k) { apply(k << 1 | 0, mat[k]); apply(k << 1 | 1, mat[k]); mat[k] = mat_ident; } void pull(int k) { vec[k] = vec_vec(vec[k << 1], vec[k << 1 | 1]); } void update(int a, int b, Mat v, int k, int l, int r) { if (r <= a || b <= l) return; if (a <= l && r <= b) { apply(k, v); return; } push(k); update(a, b, v, k << 1 | 0, l, l + r >> 1); update(a, b, v, k << 1 | 1, l + r >> 1, r); pull(k); } void update(int a, int b, Mat v) { update(a, b, v, 1, 0, N); } Vec query(int a, int b, int k, int l, int r) { if (r <= a || b <= l) return vec_ident; if (a <= l && r <= b) return vec[k]; push(k); Vec vl = query(a, b, k << 1 | 0, l, l + r >> 1); Vec vr = query(a, b, k << 1 | 1, l + r >> 1, r); return vec_vec(vl, vr); } Vec query(int a, int b) { return query(a, b, 1, 0, N); } }; int main() { cin.tie(nullptr); ios::sync_with_stdio(false); cout << fixed << setprecision(15); int N; cin >> N; vector> G(N); rep(i, N - 1) { int a, b; cin >> a >> b; G[a].push_back(b); G[b].push_back(a); } int k = 0; vector par(N, -1); vector L(N); vector R(N); vector L2(N, 1e9); vector R2(N, -1e9); vector label(N); vector label_inv(N); queue q; q.push(0); while (!q.empty()) { int u = q.front(); q.pop(); L[u] = k + 1; for (int v : G[u]) if (v != par[u]) { label[v] = ++k; label_inv[label[v]] = v; par[v] = u; q.push(v); } R[u] = k + 1; } rep(u, N) for (int v : G[u]) if (v != par[u]) { L2[u] = min(L2[u], L[v]); R2[u] = max(R2[u], R[v]); }; vector A(N); rep(i, N) cin >> A[i]; lazy_segtree, ll> seg(N, [&](int i) { return make_pair(A[label_inv[i]], 1); }, make_pair(0, 0), -1, [](pair a, pair b) { return make_pair(a.first + b.first, a.second + b.second); }, [](ll a, pair b) { return a == -1 ? b : make_pair(a * b.second, b.second); }, [](ll a, ll b) { return a != -1 ? a : b; } ); int Q; cin >> Q; while (Q--) { int x; cin >> x; ll s = 0; auto f = [&](int l, int r) { if (l <= r) { s += seg.query(l, r).first; seg.update(l, r, 0); } }; f(L[x], R[x]); f(L2[x], R2[x]); if (par[x] != -1) { int p = par[x]; f(label[p], label[p] + 1); f(L[p], R[p]); if (par[p] != -1) { int pp = par[p]; f(label[pp], label[pp] + 1); } } f(label[x], label[x] + 1); seg.update(label[x], label[x] + 1, s); cout << s << '\n'; } }