给定一棵有$n$个节点的带边权树和$q$组询问,第$i$条边的边权为$w_i$。对于每组询问,给定$m$个关键点$k_i$,你要给出一个边集使得割掉这些边会$1$号节点无法到达任意一个关键点。
为了方便,你只需要求出这个边集所包含的边的最小边权就行了。
$\texttt{Data Range}:2\leq 2\leq 2.5\times 10^5,m\geq 1,\sum k_i\leq 5\times 10^5,w_i\leq 10^5$
前言
生地终于考完了,我是不能阿克的。
链接
题解
这道题普通$\texttt{dp}$显然是$O(nm)$的,布星,只有$\texttt{40 pts}$,吸氧后还是只有$\texttt{50 pts}$。
所以说,怎么做呢?
注意到,$\sum k_i\leq 5\times 10^5$,所以,这道题能不能考虑对关键点动(luan)动(gao)手(yi)脚(xia)呢?
没错,是可以的。手玩样例可以发现,有很多点是没有用到的,于是,何不建一棵新的树,使得这棵树只包含所有用到的点呢?
这是可行的。我们想建的树,就叫做虚树。
虚树的建立
首先,第一个问题,虚树上究竟会有哪些点?
很明显,为了要维持原来的树的祖先关系,所有点间两两的$\texttt{lca}$也要算上。
所以说,建树的复杂度是$O(m^2\log n)$的?
非也,非也。把所有的标记点按$\texttt{dfs}$序排序,在相邻两点求$\texttt{lca}$即可。证明略。
于是建树的复杂度变成了$O(m\log n)$。实际操作的话就用单调栈维护一下就好了,$\texttt{dp}$的话,还是原来那么做呀。
时间复杂度$O(\sum k\log \sum k)$
代码
1 |
|