# | 제출 시각 | 아이디 | 문제 | 언어 | 결과 | 실행 시간 | 메모리 |
---|---|---|---|---|---|---|---|
1108191 | keunbum | 경주 (Race) (IOI11_race) | C++17 | 0 ms | 0 KiB |
이 제출은 이전 버전의 oj.uz에서 채점하였습니다. 현재는 제출 당시와는 다른 서버에서 채점을 하기 때문에, 다시 제출하면 결과가 달라질 수도 있습니다.
#include <bits/stdc++.h>
using namespace std;
#ifdef LOCAL
#include "debug.h"
#else
#define debug(...)
#endif
int best_path(int N, int K, int H[][2], int L[]) {
int n = N;
int k = K;
vector<vector<pair<int, int>>> g(n);
for (int i = 0; i < n - 1; ++i) {
int x = H[i][0];
int y = H[i][1];
int z = L[i];
g[x].emplace_back(y, z);
g[y].emplace_back(x, z);
}
vector<bool> removed(n, false);
vector<int> sz(n);
vector<int> pv(n);
function<void(int)> DFS = [&](int v) -> void {
sz[v] = 1;
for (auto [u, _] : g[v]) {
if (u != pv[v] && !removed[u]) {
pv[u] = v;
DFS(u);
sz[v] += sz[u];
}
}
};
auto GetCenter = [&](int r) {
pv[r] = -1;
DFS(r);
int tot = sz[r];
while (true) {
int nr = -1;
for (auto [u, _] : g[r]) {
if (u != pv[r] && !removed[u] && sz[u] * 2 > tot) {
nr = u;
break;
}
}
if (nr == -1) {
return r;
}
r = nr;
}
};
int ans = n;
int iter = 0;
vector<int> aux(k + 1, 0);
vector<int> dp(k + 1, 0);
function<void(int, int, int, int)> Find = [&](int v, int pv, int dist, int depth) -> void {
if (dist > k) {
return;
}
if (aux[k - dist] == iter) {
ans = min(ans, dp[k - dist] + depth);
}
if (dist == k) {
ans = min(ans, depth);
}
for (auto [u, w] : g[v]) {
if (!removed[u] && u != pv) {
Find(u, v, dist + w, depth + 1);
}
}
};
function<void(int, int, int, int) Calc = [&](int v, int pv, int dist, int depth) -> void {
if (dist > k) {
return;
}
if (aux[dist] < iter) {
aux[dist] = iter;
dp[dist] = depth;
} else
if (dp[dist] > depth) {
aux[dist] = iter;
dp[dist] = depth;
}
for (auto [u, w] : g[v]) {
if (!removed[u] && u != pv) {
Calc(u, v, dist + w, depth + 1);
}
}
};
function<void(int)> Solve = [&](int v) -> void {
v = GetCenter(v);
iter += 1;
for (auto [u, w] : g[v]) {
if (!removed[u]) {
Find(Find, u, v, w, 1);
Calc(Calc, u, v, w, 1);
}
}
removed[v] = true;
for (auto [u, _] : g[v]) {
if (!removed[u]) {
Solve(u);
}
}
};
Solve(0);
return (ans == n ? -1 : ans);
}