题目链接:
简单的树形DP。
设(f[x][0/1])表示在以(x)为根的子树内选/不选(x)的最大答案。
有转移:
(f[x][0]=sum max(f[y][0],f[y][1]))
(f[x][1]=1+sum f[y][0])
时间复杂度 (O(n))
代码:
#include <cstdio>
#include <vector>
#include <algorithm>
int n,f[50005][2];
std::vector<int> g[50005];
void DP(const int x,const int Pre)
{
f[x][1]=1;
for(int i=0,y;i<(int)g[x].size();++i)
if((y=g[x][i])!=Pre)
{
DP(y,x);
f[x][0]+=std::max(f[y][0],f[y][1]);
f[x][1]+=f[y][0];
}
}
int main()
{
scanf("%d",&n);
for(int i=1,x,y;i<n;++i)
{
scanf("%d%d",&x,&y);
g[x].push_back(y);
g[y].push_back(x);
}
DP(1,0),printf("%d
",std::max(f[1][0],f[1][1]));
return 0;
}