在硬盘里翻到了当时没推完的这个题,今天补完了最后几步。
题目链接:https://hydro.ac/d/bzoj/p/4321
对任意相邻两个元素差的绝对值不为 1 的 n 阶排列计数。
O(n2) 做法是考虑按照值域由小到大逐步插入,记录 fi,j 为长度为 i 的排列,一共有 j 对冲突的。每次考虑插入下一个数,发现还要记录一维当前 i 和 i−1 是否相邻这个信息,然后就能转移了。
然后下面是 O(n) 的做法。
首先考虑容斥,首先将排列划分成若干极长的值域连续段,如果一段长度为 1 那么其容斥系数为 1,否则长度为 k 的连续段容斥系数为 2×(−1)k−1,这里要乘 2 是因为有上升和下降两种方式。考虑其 OGF F(x)=x−2x2+2x3−2x4+⋯=x(21+x−1)=x1−x1+x,枚举一共有 n 段,即得答案的 OGF H(x)=∑n≥0xn(1−x1+x)n,首先如果令 G(x)=∑n≥0n!xn,其为超几何函数,微分有限,而 F 是代数形式幂级数,从而 H=G(F) 微分有限,存在整式递推。
手算一下!
G′(x)=∑n≥0n!xn−1nx2G′(x)=∑n≥0n!xn+1nx2G′(x)+∑n≥0n!xn+1=∑n≥1n!xnx2G′+xG=G−1x2G′+(x−1)G+1=0
凑出这个之后,将 F(x) 代入 x,然后整体乘 F′(x)=dF(x)dx 把 H′ 凑出来。
x2dG(x)dx+(x−1)G+1=0F(x)2dG(F(x))dx+(F(x)−1)G(F(x))F′(x)+F′(x)=0F(x)2H′(x)+(F(x)−1)H(x)F′(x)+F′(x)=0
其中 F(x)=x1−x1+x,F′(x)=−x2+2x−1(1+x)2,代入进去并整理可得:
x2(1−x)2(1+x)2H′(x)=−x4−2x3−2x+1(1+x)3H(x)+x2+2x−1(1+x)2(x5−x4−x3+x2)H′(x)=(−x4−2x3−2x+1)H(x)+(x3+3x2+x−1)
n≥4 时左右两边提取 [xn] 可得:
(n−4)hn−4−(n−3)hn−3−(n−2)hn−2+(n−1)hn−1=−hn−4−2hn−3−2hn−1+hn
即得整式递推:
hn=(n+1)hn−1−(n−2)hn−2−(n−5)hn−3+(n−3)hn−4
代码。
【推荐】国内首个AI IDE,深度理解中文开发场景,立即下载体验Trae
【推荐】编程新体验,更懂你的AI,立即体验豆包MarsCode编程助手
【推荐】抖音旗下AI助手豆包,你的智能百科全书,全免费不限次数
【推荐】轻量又高性能的 SSH 工具 IShell:AI 加持,快人一步
· TypeScript + Deepseek 打造卜卦网站:技术与玄学的结合
· Manus的开源复刻OpenManus初探
· 三行代码完成国际化适配,妙~啊~
· .NET Core 中如何实现缓存的预热?
· 阿里巴巴 QwQ-32B真的超越了 DeepSeek R-1吗?