通道 WC2018

[WC2018] 通道

genlib 真是太好用了。

题目链接: [WC2018] 通道

题目描述:

给你三棵树 T1,T2,T3T_1,T_2,T_3

maxa,b{dist1(a,b)+dist2(a,b)+dist3(a,b)}\max\limits_{a,b}\{dist_1(a,b)+dist_2(a,b)+dist_3(a,b)\}

n105n\le 10^5

这一看就是一个类似树的直径的东西。于是考虑边分治。在 T1T_1 上边分治后会得到左右两个点集,不妨记为 A,BA,B 。设这些点到其中一个中心边的端点的距离为 valaval_a ,那么就有 dist1(a,b)=vala+valbdist_1(a,b)=val_a+val_b ,其中 aA,bBa\in A,b\in B

此时式子变为最大化 vala+valb+dist2(a,b)+dist3(a,b)val_a+val_b+dist_2(a,b)+dist_3(a,b) ,此时可以在 T2T_2 上继续边分治,然后在 T3T_3 上建立虚树,获得 O(nlog2n)O(n\log^2n) 的复杂度以及 O()O(\infty) 的常数,不可取。所以只能将 A,BA,B 点集中的点在 T2T_2 中建立虚树。设某一点 aa 到虚树根节点的距离为 dad_a ,那么就有 dist2(a,b)=da+db2dlca(a,b)dist_2(a,b)=d_a+d_b-2d_{lca(a,b)}

然后,自然的,在虚树上枚举他们的 lcalca ,设为 LL ,那么式子变为最大化 (vala+da)+(valb+db)+dist3(a,b)2dL(val_a+d_a)+(val_b+d_b)+dist_3(a,b)-2d_L 。其中 dLd_L 是常数,可以忽略。那么剩下的就是一个类似于带权树的直径的东西。这个东西可以通过对于 T3T_3 的每个节点 ii ,新建一条边连向 ii 和虚节点 i+ni+n ,边权为 vali+dival_i+d_i ,然后就变成了最大化 dist3(a,b)dist'_3(a,b) ,这是一个标准的树的直径问题。但是有 aA,bBa\in A,b\in B 的限制,我们必须在 O(1)O(1)O(logn)O(\log n) 的复杂度内解决。

由于边带正权,那么有如下定理:

对于点集 A,BA,B ,树上 ABA\cup B 的直径的端点必然是 AA 直径的端点和 BB 直径的端点中的两个。

那么只需要合并儿子贡献就行了。

特别的,统计答案应该在合并儿子贡献时统计,不然无法保证 lcalcaLL 。合并儿子需要枚举 66 种情况,统计答案要枚举 88 种情况,都枚举到就行了。

代码写了 6KB6KB ,不放了。