KTT

· · 算法·理论

解决问题:

给定 n 个一次函数 y=k_ix_i+b_i 要支持一下操作:

  1. 查询 \max_{i=l}^{r} kx_i+b_i

其中满足 p \ge 0

发现如果只有 2,3 操作就是简单题了。

加上 1 操作的话就需要 KTT (Kinetic tournament tree) 来维护,KTT 就是线段树的一个变种。

1 操作不好维护的原因是因为每个位置增加的值不同,最大值位置可能发生改变,线段树每个节点在正常维护 l,r,mx 的基础上多维护一个 itr,b (交替阈值,区间最大值所取的函数所对斜率),表示这整个区间至少加多少后区间最大值位置会有变化,以这题为例 itr=\min\{ls_{itr},rs_{itr},\frac{ls_{mx}-rs_{mx}}{ls_{b}-rs_{b}}\} 线段树修改时,对于区间 [l,r]d 则让其 itr\to itr-d。若此时 itr\leq 0 则暴力将该子树所有标记下放直至遇到 itr>0 的节点。

时间复杂度在 EI 的文章 中有详细的讲解。

KTT 解决的问题需满足函数 x 增值均为正或均为负。

考虑几个问题:

旅行规划(弱化)

给定一个长为 n 的序列,支持两种操作:

  1. 区间加等差数列( a,a+p,a+2p )。
  2. 查询区间最大值。

其中保证等差数列中任意元素均大于 0。

让序列第 ik_i=i 即可转化为第一个问题,每次操作拆分成:

i\in [l,r],\; x_i+p i\in [l,r],\; b_i-(l-1)p

查询与第一个问题相同。

EI 的第六分块

给定一个长为 n 的序列,支持两种操作:

  1. 区间加。
  2. 查询区间最大子段和。

根据小白逛公园的思想,区间 [l,r] 维护 lx,rx,mx 分别表示必须包含左或右端点的最大子段和,当前整个区间的最大子段和。

每个节点维护三个函数 y=kx+b 表示区间三种最大子段和,k 为三种最大子段和所对子段的长度。b 为三种最大子段和当前的和。[l,r]d,相当于 x\to x+ditr 要考虑三种最大子段和每一种的更新。

有一个需要注意,在取到最大子段和的前提下要使长度尽量长 (斜率越大增长越快)。

P6792 区间加

跟 EI 的第六分块基本一致,吉司机线段树 + KTT,把 EI 的第六分块中的 y=kx+bk 改为最大子段和所对子段中包含区间最小值的个数即可。