您的位置:首页 > 其它

解决自然数幂和的方法

2016-03-08 12:51 197 查看

题意

∑i=1nimmodp\sum_{i=1}^{n}{i^m}\mod p

暴力

呵呵,快速幂

高斯消元

从k次,推到k+1次,求系数

矩阵乘法

有点复杂,向下面的算法一样,可以从k次,推到k+1次

倍增

像快速幂一样,打一个f[i][j]

拉格朗日插值法

就是设一个函数再把式子推出来。道理很简单,不细讲。

如需了解差分表,拉格朗日插值法

牛顿插值法

还不会

差分表

我们知道式子a

(n+1)k+1−nk+1=C1k+1∗nk+……+Ckk+1∗n+1(n+1)^{k+1}-n^{k+1}=C_{k+1}^1*n^k+……+C_{k+1}^k*n+1(二项式定理)

那么我们转换到

(n+1)k+1−1=∑i=0n(n+1)i+1−ni+1(n+1)^{k+1}-1=\sum_{i=0}^{n}(n+1)^{i+1}-n^{i+1}

根据式子a

我们可以得到

(n+1)k+1−1=C1k+1∑i=nn∗ik+……+Ckk+1∑i=nn∗i+n+1(n+1)^{k+1}-1=C_{k+1}^1\sum_{i=n}^{n}*i^k+……+C_{k+1}^k\sum_{i=n}^{n}*i+n+1

进一步得到式子b

∑i=nnik=1k+1[(n+1)k+1−C2k+1∑i=nn∗ik−1−……−Ckk+1∑i=nn∗i−n−1]\sum_{i=n}^{n}i^k={1\over{k+1}}[(n+1)^{k+1}-C_{k+1}^2\sum_{i=n}^{n}*i^{k-1}-……-C_{k+1}^k\sum_{i=n}^{n}*i-n-1]

很明显这些式子与所有的1到n的1到k-1次幂有关,所以是一个递推式



S(n,k)=∑i=nnikS(n,k)=\sum_{i=n}^{n}i^k

用s代替式子b中的部分

S(n,k)=1k+1[(n+1)k+1−C2k+1S(n,k−1)−……−Ckk+1S(n,1)−n−1]S(n,k)={1\over{k+1}}[(n+1)^{k+1}-C_{k+1}^2S(n,k-1)-……-C_{k+1}^kS(n,1)-n-1]

我们初始化s(n,0)=n+1(因为题目要求0^0=1),s(n,1)=n(n+1)/2

那么就可以递推着做自然数幂和了。

如需了解差分表,请转差分表

伯努利数

伯努利数原本就是处理等幂和的问题。

可以推得

∑i=nnik=1k+1∑i=1k+1Cik+1∗Bk+1−i∗(n+1)i\sum_{i=n}^{n}i^k={1\over{k+1}}\sum_{i=1}^{k+1}C_{k+1}^i*B_{k+1-i}*(n+1)^i

因为

∑k=0nCkn+1Bk=0(B0=1)\sum_{k=0}^nC_{n+1}^kB_k=0(B_0=1)

所以

Bn=−1n+1(C0n+1B0+C1n+1B1+……Cn−1n+1Bn−1)B_n={- {1\over{n+1}}}(C_{n+1}^0B_0+C_{n+1}^1B_1+……C_{n+1}^{n-1}B_{n-1})

伯努利数的证明十分复杂,有些东西其实可以不用弄懂,当做一个黑盒算法。

公式简单易记。

第一类斯特林数(Stirling)

其实第一类斯特林数的概念十分好懂。

如需了解第一类斯特林数,请转第一类斯特林数

首先我们设

Sk(n)=∑i=0nikS_k(n)=\sum_{i=0}^ni^k

根据第一类斯特林数的定义(P是排列数,C是组合数,s是Stirling)

Ckn=Pknk!=∑ki=0(−1)i+ks(k,i)nik!C_n^k={P_n^k\over k!}={\sum_{i=0}^k(-1)^{i+k}s(k,i)n^i\over k!}

那么我们用P每次减去一个少一位的对应斯特林式子就得到了jkj^k,在求和就是Sk(n)S_k(n)。

所以

Sk(n)=S_k(n)=

∑j=0n(k!Cjk−∑i=0k−1(−1)i+ks(k,i)ji)\sum_{j=0}^n(k!C_k^j-\sum_{i=0}^{k-1}(-1)^{i+k}s(k,i)j^i)

拆括号

=k!∑j=0nCjk−∑i=0k−1(−1)i+ks(k,i)∑j=0nji=k!\sum_{j=0}^nC_k^j-\sum_{i=0}^{k-1}(-1)^{i+k}s(k,i)\sum_{j=0}^nj^i

因为∑ni=0Cim=Cn+1m+1(证明:Cn+1m+1=Cnm+Cnm+1,那么等式两边就把Cnm消掉了,然后Cnm+1=Cm+1n−1+Cn−1m,然后又把Cn−1m消掉了,一次类推,最后全部都消掉了)\sum_{i=0}^nC_m^i=C_{m+1}^{n+1}(证明:C_{m+1}^{n+1}=C_m^n+C_{m+1}^n,那么等式两边就把C_m^n消掉了,然后C_{m+1}^n=C{m+1}^{n-1}+C_m^{n-1},然后又把C_m^{n-1}消掉了,一次类推,最后全部都消掉了)

=k!Cn+1k+1−∑i=0k−1(−1)i+ks(k,i)Si(n)=k!C_{k+1}^{n+1}-\sum_{i=0}^{k-1}(-1)^{i+k}s(k,i)S_i(n)

在转换为用排列数的

=Pk+1n+1k+1−∑i=0k−1(−1)i+ks(k,i)Si(n)={P_{n+1}^{k+1}\over k+1}-\sum_{i=0}^{k-1}(-1)^{i+k}s(k,i)S_i(n)

那么我们只需要用O(k2)O(k^2)地预处理出第一类斯特林数,然后按k来递推了,边界是S1(n)=n(n+1)/2S_1(n)=n(n+1)/2

主要运用了第一类斯特林数与排列式P的关系。

不知道WerKeyTom_FTD为什么搞出个带不带符号那么麻烦……

关系

转载并详细解说自GEOTCBRL%%%

打blog的灵感来自看了WerKeyTom_FTD

不过自我感觉十分详细。
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: