Submission #1370621

#TimeUsernameProblemLanguageResultExecution timeMemory
1370621kaiboyDesignated Cities (JOI19_designated_cities)C++20
100 / 100
193 ms43240 KiB
#include <algorithm>
#include <iostream>

using namespace std;

const       int   N = 200000;
const       int  N_ = 1 << 18;
const long long INF = 0x3f3f3f3f3f3f3f3fLL;

int ij[N], ww[N << 1], *eh[N], eo[N];
long long ans[N + 1];
long long ss[N], tt[N]; int jj[N];
long long x1, x2; int i2, j2;
long long st[N_ << 1], lz[N_]; int h_, n_;
int hh[N], ii[N], aa[N], bb[N]; bool used[N];

void append(int i, int h) {
	int o = eo[i]++;
	if (!o)
		eh[i] = (int *) malloc(sizeof *eh[i]);
	else if (!(o & o - 1))
		eh[i] = (int *) realloc(eh[i], (o << 1) * sizeof *eh[i]);
	eh[i][o] = h;
}

long long dfs0(int h_, int i) {
	long long s = 0;
	for (int o = 0; o < eo[i]; o++) {
		int h = eh[i][o];
		if ((h ^ 1) != h_) {
			int j = i ^ ij[h >> 1], w = ww[h];
			s += w + dfs0(h, j);
		}
	}
	return ss[i] = s;
}

void dfs1(int h_, int i, long long s_) {
	long long s = 0;
	for (int o = 0; o < eo[i]; o++) {
		int h = eh[i][o];
		if ((h ^ 1) != h_) {
			int j = i ^ ij[h >> 1], w = ww[h];
			s += w + ss[j];
		}
	}
	x1 = min(x1, s + s_);
	if (h_ != -1 && eo[i] == 1) {
		tt[i] = 0, jj[i] = i;
		return;
	}
	long long t_ = INF; int j_ = -1;
	for (int o = 0; o < eo[i]; o++) {
		int h = eh[i][o];
		if ((h ^ 1) != h_) {
			int j = i ^ ij[h >> 1], w = ww[h];
			dfs1(h, j, s + s_ + ww[h ^ 1] - (w + ss[j]));
			long long t = tt[j] - (w + ss[j]);
			if (j_ != -1) {
				long long x = s + s_ + t + t_;
				if (x2 > x)
					x2 = x, i2 = jj[j], j2 = jj[j_];
			}
			if (t_ > t)
				t_ = t, j_ = j;
		}
	}
	tt[i] = s + t_, jj[i] = jj[j_];
}

void dfs2(int h_, int i, long long s) {
	static int a = 0;
	hh[i] = h_;
	if (h_ != -1 && eo[i] == 1) {
		st[a + n_] = s;
		ii[aa[i] = a++] = i;
		bb[i] = a;
		return;
	}
	aa[i] = a;
	for (int o = 0; o < eo[i]; o++) {
		int h = eh[i][o];
		if ((h ^ 1) != h_) {
			int j = i ^ ij[h >> 1], w = ww[h];
			x2 += w, dfs2(h, j, s + w);
		}
	}
	bb[i] = a;
}

void put(int i, long long a) {
	st[i] += a;
	if (i < n_)
		lz[i] += a;
}

void pus(int i) {
	if (lz[i]) {
		int l = i << 1, r = l ^ 1;
		put(l, lz[i]);
		put(r, lz[i]);
		lz[i] = 0;
	}
}

void pul(int i) {
	if (!lz[i]) {
		int l = i << 1, r = l ^ 1;
		st[i] = max(st[l], st[r]);
	}
}

void push(int i) {
	for (int h = h_; h; h--)
		pus(i >> h);
}

void pull(int i) {
	while (i >>= 1)
		pul(i);
}

void build(int n) {
	for (h_ = 0, n_ = 1; n_ < n; h_++, n_ <<= 1)
		;
	x2 = 0, dfs2(-1, i2, 0);
	for (int i = n_ - 1; i; i--)
		pul(i);
}

void update(int l, int r, int a) {
	int l_ = l += n_, r_ = r += n_;
	push(l_), push(r_);
	for ( ; l <= r; l >>= 1, r >>= 1) {
		if (l & 1)
			put(l++, a);
		if (!(r & 1))
			put(r--, a);
	}
	pull(l_), pull(r_);
}

int query() {
	int i = 1;
	while (i < n_)
		pus(i), i = i << 1 ^ st[i << 1] < st[i];
	return i - n_;
}

int main() {
	ios_base::sync_with_stdio(false), cin.tie(NULL);
	int n; cin >> n;
	for (int h = 0; h < n - 1; h++) {
		int i, j, w, w_; cin >> i >> j >> w >> w_, i--, j--;
		ij[h] = i ^ j, ww[h << 1 ^ 0] = w, ww[h << 1 ^ 1] = w_;
		append(i, h << 1 ^ 0), append(j, h << 1 ^ 1);
	}
	dfs0(-1, 0);
	x1 = x2 = INF;
	dfs1(-1, 0, 0);
	ans[1] = x1;
	if (x2 > tt[0])
		x2 = tt[0], i2 = 0, j2 = jj[0];
	int m = 0;
	for (int i = 0; i < n; i++)
		if (i != i2 && eo[i] == 1)
			m++;
	build(m);
	for (int k = 2; k <= n; k++) {
		ans[k] = x2 -= st[1];
		int i = ii[query()];
		while (true) {
			int h = hh[i];
			if (h == -1 || used[h >> 1])
				break;
			used[h >> 1] = true;
			update(aa[i], bb[i] - 1, -ww[h]);
			i ^= ij[h >> 1];
		}
	}
	int q; cin >> q;
	while (q--) {
		int k; cin >> k;
		cout << ans[k] << '\n';
	}
	return 0;
}
#Result Execution timeMemoryGrader output
Fetching results...
#Result Execution timeMemoryGrader output
Fetching results...
#Result Execution timeMemoryGrader output
Fetching results...
#Result Execution timeMemoryGrader output
Fetching results...
#Result Execution timeMemoryGrader output
Fetching results...
#Result Execution timeMemoryGrader output
Fetching results...