1 条题解

  • 0
    @ 2026-5-14 14:00:22

    题目重述

    我们有一棵 nn 个结点的树。
    每次操作:选择 sstt,把 sstt 的唯一路径上的所有点(除了 ss)直接连接为 ss 的孩子(即删除原路径上的边,添加 ss 到这些点的边)。
    问:最少需要多少次操作,才能使得树的直径最小?


    关键观察

    1. n=2n = 2
      直径已经是 11,不需要操作,答案为 00

    2. n>2n > 2
      可以证明最小的直径只能是 22
      为什么?
      因为我们可以任选一个根 rr,然后反复操作使其它所有结点都直接成为 rr 的孩子(即深度为 11),这样任意两个叶子之间的距离最多为 22(经过 rr)。
      所以最小直径可达 22

      因此,问题转化为:通过最少操作,使所有结点深度 ≤ 1(相对于某根 rr


    操作与深度的关系

    固定根 rr,定义:

    • dud_uuu 在树中的深度(dr=0d_r = 0,孩子深度 == 父深度 +1+1)。
    • 初始树中,深度 >1> 1 的结点需要被“拉”到深度 11

    在一次操作中:

    • 选择路径 sts \to t,删除路径上的边,再把 tt 及其中间结点连到 ss
    • 注意:一次操作只能让路径末端的一个叶子(以及中间结点)提升到离 ss 更近的位置。
    • 实际上,一次操作最多可以将一条从 rr 出发到某个深度 >1>1 的叶子的路径上的所有点变为 rr 的直接孩子。

    因此:

    • 对于深度 >1>1 的叶子,每个这样的叶子至少需要一次操作(才能让它成为 rr 的孩子)。
    • 一次操作可以处理一条从 rr 出发的路径上多个深度 >1 的点,但只能消除一个深度 >1 的叶子(因为路径末端必须是叶子)。

    结论:
    若固定根 rr,最少操作数 = 深度 >1> 1 的叶子数量。


    优化根的选择

    因为我们可以自由选择 rr,所以要最小化:

    $$\text{操作数} = \min_{r} \left( \text{深度} > 1 \text{ 的叶子数} \right) $$

    等价转换

    深度 >1>1 的叶子 = 叶子总数 − 深度 =1=1 的叶子。

    而深度 =1=1 的叶子就是根 rr 的邻居中为叶子的那些结点。
    c1c_1 = 整棵树叶子总数。
    mrm_r = 根 rr 的邻居中叶子的数量。

    那么对于根 rr,操作数 = c1mrc_1 - m_r

    所以:

    答案=c1maxrmr\text{答案} = c_1 - \max_{r} m_r

    其中 mrm_r = 与 rr 相邻的叶子结点数。


    最终解法

    1. 读入树,计算每个结点的度数 deg(u)\deg(u)
    2. 叶子结点定义为 deg(u)=1\deg(u) = 1
    3. 计算 c1c_1 = 叶子总数。
    4. 对每个结点 uu,计算 mum_u = 它的邻居中是叶子的数量。
    5. mmax=maxumum_{\max} = \max_u m_u
    6. 答案 = c1mmaxc_1 - m_{\max}
    7. 特判 n3n \le 3 时答案为 00(因为此时直径已经 ≤ 2)。

    示例验证

    以第一个样例(n=4n=4,边:1-2, 1-3, 2-4)为例:

    • 叶子:3, 4 → c1=2c_1 = 2
    • 结点 1:邻居 2(度2), 3(度1) → m1=1m_1 = 1
    • 结点 2:邻居 1(度2), 4(度1) → m2=1m_2 = 1
    • 结点 3:邻居 1(度2) → m3=0m_3 = 0
    • 结点 4:邻居 2(度2) → m4=0m_4 = 0
    • mmax=1m_{\max} = 1
    • 答案 = 21=12 - 1 = 1

    符合题目输出。


    复杂度

    • 每个结点遍历邻居一次。
    • 总复杂度 O(n)O(n)
    • 满足所有测试用例 nn 总和 ≤ 2×1052\times 10^5

    对应 Python 标程思路

    c1 = sum(deg[u] == 1 for u in range(n))
    mx = max(sum(deg[v] == 1 for v in g[u]) for u in range(n))
    return c1 - mx if n > 3 else 0
    

    完全符合上述推导。

    • 1

    信息

    ID
    7044
    时间
    1000ms
    内存
    256MiB
    难度
    5
    标签
    递交数
    1
    已通过
    1
    上传者