Luogu10144 [WC/CTS2024] 水镜

题意:水池中有 个石柱,高度分别为

水池的水位为 ,则第 个石柱的像的高度为

泉水精灵可以栖息在石柱或石柱的像上,并从左到右行走,高度必须单调递增。

询问有多少对 满足存在一种水位 使得泉水精灵可以从第 个石柱(或它的像)到达地 个石柱(或它的像)。

,时限


算法一:

枚举 ,再枚举 种选择,判断是否存在一种选择满足

复杂度 ,可以通过测试点 ,期望得分

算法二:

建立图论模型:对所有 ,在平面直角坐标系上标记点 ,共 个点。对于两个被标记的点 ,若满足 ,则连接有向边 。本质上,我们想探究这张有向图的可达性。

是固定不动的,点 会随着 的变化而运动,相邻层之间的连边有 种可能的情况,每种情况生效的 都是一个区间。

于是,我们可以将 的可能取值划分为 个区间,每个区间内,有向图的结构都不变。

对于确定的图,简单 搜索(或递推)即可求出所有好对子,总复杂度

复杂度 ,可以通过测试点 ,期望得分

算法三:

沿用算法二的思路,对 分段讨论。

对于确定的图,按 坐标从左往右 DP,记 为在点 结束的路径出发点 坐标的最小值,转移显然。所有的 可以 求出。

,则 都是好对子。

对每个 记录 的最小值,则好对子总数为

复杂度 ,可以通过测试点 ,期望得分

算法四:

,存在符合题意的 当且仅当:存在 ,使得 严格递减, 严格递增。 之间是等号、不等号都可以。

形式化地,我们想要的是

从小到大增加, 之间的不等号会逐个改变,可以用 std::set 维护合法的极长“”区间。区间每次变化时(注意,可能有多个不等号同时变化),记下新的区间 ,使用单调栈求出所有区间的下包络,容易求出子区间总数。

复杂度 ,期望得分

算法五:

延续算法四的思路, 可以转化为 中不存在

考虑水位变化给 带来的影响。我们只关心相邻的 的相对大小,不妨设 ,分类讨论可知

  • 时,
  • 时,
  • 时,

另一种情况类似。

对于每个 ,“不存在 ”都对 提出一个约束,形如“ 不属于某区间”。

现在问题就转化成,给出 个区间 ,求有多少对 满足 的并不是全集。

考虑用扫描线解决,枚举 ,我们要找到所有符合题意的

先离散化,每次 右移,新加入一个区间 ,将数组 的区间 赋值为 。这样,数组 中的最小值 就是最薄弱的位置, 时能覆盖全集, 时不能。

(或者用双指针解决)复杂度 ,期望得分

算法六:

延续算法五的思路,仍然求有多少对 满足 的并不是全集。

这些区间具有特殊性,通过复杂的讨论可以发现, 的并中至多有三个独立的区间,于是信息可以 储存与合并。

使用不可删双指针即可做到