1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
| #include <cstdio>
#include <cstring>
#include <algorithm>
const int INF(0x3FFFFFFF);
struct tree_node
{
int left, right;
} tree[150];
int root, n, p, last[150], f[150][150], son[150];
bool notroot[150];
int dp(const int i, const int j)
{
if (i == -1) return j == 0 ? 0 : INF;
if (j == 0) return 0;
if (j < 0) return INF;
if (f[i][j] != -1) return f[i][j];
int res = 1+dp(tree[i].right, j-son[i]-1);
for (int k = 0; k <= j; ++k)
res = std::min(res,
dp(tree[i].left, k)+dp(tree[i].right, j-k)
);
return f[i][j] = res;
}
int getson(const int root)
{
int node = tree[root].left;
while (node != -1)
{
son[root] += 1+getson(node);
node = tree[node].right;
}
return son[root];
}
int main()
{
memset(f, 255, sizeof(f));
memset(tree, 255, sizeof(tree));
scanf("%d%d", &n, &p);
for (int i = 0, x, y; i < n-1; ++i)
{
scanf("%d%d", &x, &y);
--x, --y;
(last[x] ? tree[last[x]].right : tree[x].left) = y;
last[x] = y;
notroot[y] = true;
}
for (; root < n && notroot[root]; ++root);
getson(root);
int ans = dp(tree[root].left, n-p);
for (int i = 0; i < n; ++i)
if (i != root)
ans = std::min(ans, dp(tree[i].left, son[i]+1-p)+1);
printf("%d", ans);
}
|