专栏文章

题解:CF1967E2 Again Counting Arrays (Hard Version)

CF1967E2题解参与者 1已保存评论 0

文章操作

快速查看文章及其快照的属性,并进行相关操作。

当前评论
0 条
当前快照
1 份
快照标识符
@miqb0wb8
此快照首次捕获于
2025/12/04 01:52
3 个月前
此快照最后确认于
2025/12/04 01:52
3 个月前
查看原文
直接容斥,用总数量减去不合法的数量。
考虑将题目转化为一个格路计数问题:(i,ai)(i,a_i) 位置禁止经过,判定是否存在一条从 (0,b)(0,b) 出发,每次从 (x,y)(x,y) 走到 (x+1,y±1)(x+1,y\plusmn 1) 的位置能否走 nn 步。
首先对于判定问题,我们显然会优先向 (x+1,y+1)(x+1,y+1) 走,并且一旦碰到 y=my=m 这条线就寄了。所以能让我向上走有 m1m-1 种方法,但是让我向下走只有 11 种方法。
直接暴力 dp 就可以做到 O(nm)O(nm)
枚举碰到 y=1y=-1 这条线的时刻 tt,则 tt 之前的路径不能碰到 y=my=my=1y=-1 两条直线,可以使用类似 P3266 的反射容斥做到 O(n2m)O\left (\frac {n^2} m\right )
根号分治一下,我们得到了一个 O(nn)O(n\sqrt n) 复杂度的做法,可以通过 E1,code

暴力 dp 没有前途,考虑延续反射容斥的做法。我们能不能不去枚举碰到 y=1y=-1 的时刻呢?
其实是可以的。你注意到碰到 y=1y=-1 之后我们仍然需要在后面乱填,需要乘上 mntm^{n-t} 的贡献,而这等价于碰到 y=1y=-1 之后开始随便乱走。这样我们只要枚举终点的位置 pp 即可。设 (0,b)(n,p)(0,b)\to (n,p) 往上走了 kk 次,则贡献为 (m1)k(m-1)^k,这样我们只需要计算有多少条合法的路径即可。
定义一条路径合法,当且仅当它第一次碰到的边界是 y=1y=-1。考虑对 pp 的位置分类讨论:
  1. 如果 p1p\le -1,则显然你一定会碰到一次 y=1y=-1,但不一定是第一次碰到。所以需要减去先碰到上边界的方案数,然后加回先碰下再碰上的方案数……反射容斥即可。
  2. 如果 p>1p>-1,则我们可以先把碰到 y=1y=-1 之后的部分翻转下来,转化为 p1p\le -1 的问题。
我们发现,一个位置 pp,往上反射后到达 2mp2m-p,再往下反射会到达 p2m2p-2m-2。也就意味着,能对原本的 p0p_0 造成贡献的位置在 y=1y=-1 下方和 y=my=m 的上方形成了两个公差为 2m+22m+2 的等差数列,可以用类似差分的方式维护。
最后扫一遍值域还原回去。复杂度线性,code

评论

0 条评论,欢迎与作者交流。

正在加载评论...