#include <bits/stdc++.h>
using namespace std;
const int MAXN = 200005;
vector<int> g[MAXN];
int N, D;
// Funkcja rekurencyjna zwraca wektor dp[]
// dp[i] = maksymalna liczba zaznaczonych węzłów w poddrzewie,
// jeśli najbliższy zaznaczony węzeł w górę drzewa jest w odległości >= i
vector<int> dfs(int v, int par) {
// dp[d] = maks liczba zaznaczonych w poddrzewie v przy odległości d do najbliższego markowanego w górę
vector<int> dp(D+1, 0);
for (int u : g[v]) {
if (u == par) continue;
vector<int> child = dfs(u, v);
vector<int> new_dp(D+1, 0);
for (int i = 0; i <= D; i++) {
int best = 0;
for (int j = 0; j <= D; j++) {
int dist = min(D, i+1+j); // odległość do zaznaczonego w górę po połączeniu z dzieckiem
best = max(best, dp[i] + child[j]);
}
new_dp[i] = best;
}
dp = new_dp;
}
// Opcja: zaznaczamy v (tylko jeśli odległość do zaznaczonego w górę >= D)
if (D > 0) {
dp[0] = 1; // v jest zaznaczone
for (int u : g[v]) {
if (u == par) continue;
vector<int> child = dfs(u, v);
dp[0] += child[D-1]; // w dzieciach odległość = D-1
}
} else {
dp[0] = 1; // D = 0, można zaznaczyć wszystkie
}
return dp;
}
int main() {
ios::sync_with_stdio(false);
cin.tie(nullptr);
cin >> N >> D;
for (int i = 1; i < N; i++) {
int p;
cin >> p;
g[p].push_back(i);
g[i].push_back(p);
}
vector<int> res = dfs(0, -1);
cout << *max_element(res.begin(), res.end()) << "\n";
}
| # | Verdict | Execution time | Memory | Grader output |
|---|
| Fetching results... |
| # | Verdict | Execution time | Memory | Grader output |
|---|
| Fetching results... |
| # | Verdict | Execution time | Memory | Grader output |
|---|
| Fetching results... |