CF1824B2

原题

翻译

首先根据猜结论数学归纳法可以想到在k为奇数时答案依然是1

因此我们只考虑k是偶数的情况


方法1:

容易想到好点相当于这棵树上只考虑k个关键点的中心

则显然根据重心定义,我们枚举每个点为重心的情况,则对于他的每个儿子,我们可以用dp或者容斥原理来从中选出k2个点,这里重点说一下容斥原理

因为发现对于每个儿子最多有一个儿子内选的点的个数>k2,因此我们枚举是哪个儿子的子树选了这么多的点,可以得到答案(u,v)Ei=k2+1k(sizvi)(nsizvki)

这样我们就可以得到一个O(n2)的做法,但这个做法显然不够优秀

我们考虑优化一下做法,显然dp是没法再优化的,因此我们考虑优化容斥

fx=i=k2+1k(xi)(nxki)

观察fx的组合意义,我们发现fx+1相对与fx多的部分实际上就是前x个数恰好选了i+1个,和前x个数选i个第x+1个数必须选的情况

因此可以得到fx+1=fx+(xk2)(nx1kk21)

于是我们可以实现O(n)预处理O(n)计算,总复杂度O(n)


方法2:

首先可以证明好点一定对应树上的一个连通块,根据重心的定义,这是显然的(其实限制更严格,答案在树上是一条链,但这里不需要这么严格的限制)

我们考虑计算树上的点并不好算,但如果对于一条边(u,v)Euv都是好点,则把边(u,v)切开分成的两棵树中关键点的个数显然是一样的

而且由于答案在树上是一个联通快,我们可以通过联通块内边的个数+1得到联通快内点的个数

因此我们对于每条边考虑他左右两边各选k2的方案数,答案即为:

(u,v)E(sizuk2)(nsizuk2)

同样可以做到O(n)

posted @   FOX_konata  阅读(11)  评论(0编辑  收藏  举报
相关博文:
阅读排行:
· DeepSeek 开源周回顾「GitHub 热点速览」
· 物流快递公司核心技术能力-地址解析分单基础技术分享
· .NET 10首个预览版发布:重大改进与新特性概览!
· AI与.NET技术实操系列(二):开始使用ML.NET
· 单线程的Redis速度为什么快?
点击右上角即可分享
微信分享提示