[XSY] 树与图(树形DP、生成函数、分治NTT、重链剖分)

本文探讨如何将图上的算法转化为树上的操作,利用树形DP、生成函数和分治NTT优化算法。通过分析不同情况下的时间复杂度,提出在树上进行重链剖分的方法,最终实现整体的时间复杂度为O(nlog3n)。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

树与图

  • 如果真的在图上跑算法,那么光建图复杂度就 O ( n 2 l o g n ) O(n^2logn) O(n2logn)了,这显然不可行。所以一定要把 在图上的操作 转换成 在树上的操作
  • 在图上删去点u,相当于在树上删去u到根节点的链,并把u的整棵子树删掉
  • 如果我们枚举算法可能产生的所有过程,然后再去求每个过程对应的删点次数,那么光枚举过程就已经可以T爆了
  • 所以我们只能枚举删点次数,然后求出该删掉次数对应多少种过程
  • 这可以用树形DP实现,时间复杂度 O ( n 3 ) O(n^3) O(n3)
  • 可以想到用生成函数进一步优化,即用次数来代表删点次数,系数来代表可能过程种数,这样合并两棵子树时直接用NTT把两棵子树的多项式乘起来即可
  • 这样会产生两个问题:
  1. 代码中每一步合并乘的 C j + k k C_{j+k}^{k} Cj+kk怎么办?

  2. NTT的时间复杂度是 O ( n l o g n ) O(nlogn) O(nlogn) ( 这 里 n 指 多 项 式 的 最 高 次 数 ) \color{Red}(这里n指多项式的最高次数) (n),这样总时间复杂度就是 O ( n 3 l o g n ) O(n^3logn) O(n3logn),怎么还变大了?

    就是这两个问题让我在考场上没有继续写下去

  • 对于第一个问题,我后来想到,其实不一定要在DP过程中乘 C j + k k C_{j+k}^{k} Cj+kk,DP完后再统一乘 ( 删 点 次 数 ) ! (删点次数)! 来定序也是可行的
  • 对于第二个问题,在更新u时,直接用 分治NTT 把u的所有儿子上的多项式 一起 乘起来,不要那么傻逼想着用NTT一个接一个乘
    这样时间复杂度降为 O ( n 2 l o g 2 n ) O(n^2log^2n) O(n2log2n),但还是会T
  • 题目的时间复杂度很大程度上取决于NTT时多项式的最高次数,而多项式次数与删点次数有关,所以考虑一下我们最多能删几个点
  • 发现所选的要删的点满足如下规律:所选的任意两个点都不互为祖先关系,且从根到每个叶子的路径上都恰好有一个被选择的点
  • u 点 的 多 项 式 的 最 高 次 数 < = u 子 树 内 叶 节 点 的 个 数 \color{Red}u点的多项式的最高次数<=u子树内叶节点的个数 u<=u,进一步地,因为每个节点的多项式最高次数至少为1,所以 u 点 的 多 项 式 最 多 是 ( u 子 树 内 叶 节 点 个 数 ) 个 多 项 式 相 乘 的 结 果 \color{Red}u点的多项式最多是(u子树内叶节点个数)个多项式相乘的结果 u(u)
  • l e a f u leaf_u leafu表示u的子树中叶子的个数,则在u点分治NTT的时间总和 < = l e a f u ( l o g 2 l e a f u ) <=leaf_u(log^2leaf_u) <=leafu(log2leafu),整道题的总时间 < = ∑ u = 1 n l e a f u ( l o g 2 l e a f u ) <=\sum_{u=1}^{n}leaf_u(log^2leaf_u) <=u=1nleafu(log2leafu)
  • 考虑两种极端情况,一种是菊花图,一种是一条很长的树链,上面随机的挂上一些类似菊花图(深度小但点度数大)的子树
  • 按照上面的做法,菊花图的时间复杂度可以做到 O ( n l o g 2 n ) O(nlog^2n) O(nlog2n),树链的时间复杂度却逼近 O ( n 2 l o g 2 n ) O(n^2log^2n) O(n2log2n)
  • 我们考虑给树链换一种做法:
    枚举在链上删了哪个点,这样一来整条链和被删点的子树都会被删除,而被删点上方的子树不会被删除,并且相互独立了。
    因此,如果链上的点的多项式为 F 1 ( x ) , F 2 ( x ) , F 3 ( x ) . . . F_1(x),F_2(x),F_3(x)... F1(x),F2(x),F3(x)...(按点深度由浅到深编号),那么最后求出这条链的多项式为: F 1 ( x ) + F 1 ( x ) F 2 ( x ) + F 1 ( x ) F 2 ( x ) F 3 ( x ) . . . F_1(x)+F_1(x)F_2(x)+F_1(x)F_2(x)F_3(x)... F1(x)+F1(x)F2(x)+F1(x)F2(x)F3(x)...
    用分治NTT做,总时间 < = l e a f 1 ( l o g 2 l e a f 1 ) <=leaf_1(log^2leaf_1) <=leaf
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值