模板
#include<iostream>
#include<algorithm>
#include<cstring>
using namespace std;
const int N = 100010,M = N * 2;
//h是N个单链表的头节点
//ne是单链表的ne数组
//e是单个节点的值
//idx是当前可用的下标
//st是检查点有无走过
int e[M],ne[M],h[N];
int n,idx = 0;
bool st[N];
//单向联通
void add(int a,int b){
e[idx] = b;
ne[idx] = h[a];
h[a] = idx ++;
}
//深搜,遍历每一个点
void dfs(int u){
st[u] = true;
for(int i = h[u];i != -1;i = ne[i]){
int j = e[i];
if(!st[j]) dfs(j);
}
}
int main(){
cin >> n;
//点的状态初始化
memset(h,-1,sizeof h);
while(n --){
int a,b;
cin >> a >> b;
add(a,b);
}
dfs(0);
}
#include<iostream>
#include<algorithm>
#include<cstring>
using namespace std;
const int N = 100010,M = N * 2;
int e[M],ne[M],h[N];
int idx = 0;
int st[M];
int n;
int ans = N;
void add(int a,int b){
e[idx] = b;
ne[idx] = h[a];
h[a] = idx ++;
}
int dfs(int u){
st[u] = 1; //当前点走过
int sum = 1,res = 0; //sum是该点的节点数,res是连通块内点的数量
//遍历一条树枝
for(int i = h[u];i != -1;i = ne[i]){
int j = e[i]; //取出子节点下标
if(!st[j]){
int t = dfs(j); //算出子节点的节点数
sum += t;
res = max(res,t);
}
}
res = max(res,n - sum); //取连通块节点最大值
ans = min(ans,res);
return sum;
}
int main(){
cin >> n;
memset(h,-1,sizeof h); //点的状态初始化
for(int i = 1;i < n;i ++){
int a,b;
cin >> a >> b;
add(a,b),add(b,a); //无向图所以要双向加边
}
dfs(1);
cout << ans;
}