poj 2378 Tree Cutting(树形dp)

题意:n个节点的树,删除一个点,得到的最大联通分支大小不大于总节点数的一半,求这样点的集合。

#include <cstdio>
#include <vector>
#include <iostream>
#include <string.h>

using namespace std;

#define N 10010

int dp[N],n,num[N],used[N];
vector<int>e[N];
int dfs(int root)
{
    num[root]=1;
    used[root]=1;
    for(int i=0; i<e[root].size(); ++i)
    {
        int son=e[root][i];
        if(used[son])continue;
        num[root]+=dfs(son);
        dp[root]=max(dp[root],num[son]);
    }
    dp[root]=max(dp[root],n-num[root]);
    return num[root];
}
int main()
{
    int res[N];
    while(~scanf("%d",&n))
    {
        memset(dp,0,sizeof(dp));
        memset(used,0,sizeof(used));
        for(int i=1; i<=n; ++i)
            e[i].clear();
        int a,b;
        for(int i=0; i<n-1; ++i)
        {
            scanf("%d%d",&a,&b);
            e[a].push_back(b);
            e[b].push_back(a);
        }
        dfs(1);
        int l=0,f=0;
        for(int i=1; i<=n; ++i)
            if(dp[i]<=n/2)
            {
                f=1;
                printf("%d\n",i);
            }
        if(!f)printf("NONE\n");
    }
    return 0;
}

你可能感兴趣的:(poj 2378 Tree Cutting(树形dp))