[总结] 第一类斯特林数
第一类斯特林数
[nm] ,将 n 个元素划分为 m 个圆排列的方案数。
递推
递推式可以枚举最后一个元素是否放一个新的排列:[nm]=[n−1m−1]+(n−1)×[n−1m]
下面用 s(n,m) 表示 [nm]。
性质
n!=n∑i=0s(n,i)
证明:考虑其组合意义。一个排列唯一对应一个置换,而一个置换唯一对应一组轮换。比如排列 (1,5,2,3,4),就可以看作轮换组 [1][2,5,4][3]。如果两个排列不同,那他们对应的轮换中,必定有一个元素的下一个元素不同,故排列与轮换一一对应。所以等式右侧的式子就是有 0∼n 个轮换的方案数。
求法
现在要快速求出第一类斯特林数的某一行。
直接给出定义,s(n,∗) 这东西的生成函数等于 n−1∏i=0(x+i),也就是 x 的 n 次上升幂。
于是就可以分治NTT来求了,复杂度 O(nlog2n)。具体实现用vector比较好写。
当然也可以 O(nlogn)。
令 Fn(x)=n−1∏i=0(x+i),则F2n(x)=Fn(x)×Fn(x+n)。
考虑如何用 Fn(x) 快速求出 Fn(x+n)。
设 Fn(x)=n−1∑i=0aixi
Fn(x+n)=n∑i=0ai(x+n)i=n∑i=0ai×i∑j=0Cjini−jxj=n∑i=0xi×n∑j=iCijnj−iaj=n∑i=0xi×n∑j=ij!i!(j−i)!nj−iaj
所以设 Fn(x+n)=n−1∑i=0bixi,ci=i!×ai,di=nii! ,那么
bi×i!=∑jcj×dj−i
把 d 翻转以后是一个标准的卷积式子,直接倍增就好了。
实现的小细节就是,如果当前长度 len 为奇数,不能除以 2,所以直接递归 len−1 ,然后回来之后乘上 (x+len−1) 就行了。
当你走进这欢乐场
【推荐】100%开源!大型工业跨平台软件C++源码提供,建模,组态!
【推荐】AI 的力量,开发者的翅膀:欢迎使用 AI 原生开发工具 TRAE
【推荐】2025 HarmonyOS 鸿蒙创新赛正式启动,百万大奖等你挑战
· 通过 Canvas 将后端发来的一帧帧图片渲染成“视频”的实现过程
· 当加密ID需要变成Guid:为什么我选择了AES-CBC而非GCM?
· 基于 epoll 的协程调度器——零基础深入浅出 C++20 协程
· 下划线字段在golang结构体中的应用
· SQL Server也能玩正则表达式?
· C#实现屏幕墙:同时监控多个电脑桌面(支持Windows、信创Linux、银河麒麟、统信UOS)
· 我的AI自学路线,可能对你有用
· 通过Canvas在网页中将后端发来的一帧帧图片渲染成“视频”的实现过程
· 如何做一个纯净版的ABP vNext 脚手架
· 告别 DOM 的旧时代:从零重塑 Web 渲染的未来