poj1655
题目
就是给你一棵树,删掉某个点后形成的森林中节点最多的森林的节点数就是那个点的balance,现求给定树的最小balance及其编号。
思路
一遍dfs,累加一下每个节点的子节点数,在记录的同时更新最大balence值,最后要考虑一下父节点的情况,也就是n-num[u]即可。
代码
#include <iostream>
#include <cstdio>
#include <cstdlib>
#include <cstring>
#include <queue>
using namespace std;
typedef long long ll;
const int maxn=20100;
struct node
{
int next;
int to;
} edge[maxn*2];
int head[maxn],tot,num[maxn],dp[maxn],n;
void addedge(int from,int to)
{
edge[tot].to=to;
edge[tot].next=head[from];
head[from]=tot++;
}
void dfs(int u,int fa)
{
num[u]=1;
dp[u]=0;
for(int i=head[u]; ~i; i=edge[i].next)
{
int v=edge[i].to;
if(v==fa) continue;
dfs(v,u);
dp[u]=max(dp[u],num[v]);
num[u]+=num[v];
}
dp[u]=max(dp[u],n-num[u]);
}
int main()
{
int T;
scanf("%d",&T);
while(T--)
{
scanf("%d",&n);
memset(head,-1,sizeof(head));
tot=0;
for(int i=0; i<n-1; i++)
{
int a,b;
scanf("%d %d",&a,&b);
addedge(a,b);
addedge(b,a);
}
dfs(1,-1);
int maxx=0x3f3f3f3f;
int id;
for(int i=1; i<=n; i++)
{
if(maxx>dp[i])
{
maxx=dp[i];
id=i;
}
}
printf("%d %d\n",id,maxx);
}
return 0;
}