题意:
这题大意是构建一个无根的树,让你求最少几条链能把树的结点都包含在内,并且输出链(答案不唯一,输出即可)
所以输入是构建一个树。
分析+思路:
这题签到题一看到树就知道是找规律+dfs,你多画几种情况,看看结果与n的关系就可以玄学证明得出:
记叶节点为p1,p2,pn,共ans个。
最少链数=(ans+1)/2(整除);
并且输出链能完美包含的情况就是pi和pi+ans/2;(也就是如果偶数就分半,分半对应,奇数就第一个数对应最中间的那个数,最中间那个树对应最后一个树,(本来最原始的理解是分半,一一对应,出现有中间让他和任意一个对应即可))
这里本来打算老老实实模拟dfs树,但是后来突然发现,只用记录哪个是叶节点就好了,直接定义一个数组,只出现了一次的元素就是叶节点,另外定义一个数组记录下来,ans自然就也出来了,主要还是这个玄学证明。
ac代码:
#include<bits/stdc++.h>
using namespace std;
const int N=2e5+10;
int ans,a[N],u,v,p[N];
int main()
{
int n;
scanf("%d",&n);
for(int i=1;i<n;i++)
{
scanf("%d%d",&u,&v);
a[u]++,a[v]++;
}
for(int i=1;i<=n;i++)
{
if(a[i]==1)
{
p[++ans]=i;
}
}
printf("%d\n",(ans+1)/2);
for(int i=1;i<=(ans+1)/2;i++)
printf("%d %d\n",p[i],p[i+ans/2]);
}