A174605 数学证明
- 序列定义
由 Mathematica 代码可知:
a(n)=k=0∑n(k−s2(k))
其中 s2(k) 是 k 的二进制表示中 1 的个数(popcount)。
- Legendre 公式:ν2(n!)=n−s2(n)
这是核心引理。
证明: 设 n 的二进制表示为 n=∑j=0Lbj⋅2j,其中 bj∈0,1。
由 Legendre 公式,n! 中素因子 2 的幂次为:
ν2(n!)=i=1∑∞⌊2in⌋
将 n 的二进制展开代入:
⌊2in⌋=j=i∑Lbj⋅2j−i
因此:
i=1∑∞⌊2in⌋=i=1∑Lj=i∑Lbj⋅2j−i
交换求和顺序(令 j 为外层):
=j=1∑Lbji=1∑j2j−i=j=1∑Lbj⋅(2j−1)
由于 b0⋅(20−1)=0,可以从 j=0 开始:
=j=0∑Lbj⋅(2j−1)=j=0∑Lbj⋅2j−j=0∑Lbj=n−s2(n)■
- 与 Barnes G 函数的联系
Barnes G 函数满足 G(n+2)=∏k=1nk!(超阶乘)。
因此:
ν2(G(n+2))=k=1∑nν2(k!)=k=1∑n(k−s2(k))=k=0∑n(k−s2(k))=a(n)
最后一步成立是因为 k=0 时 0−s2(0)=0。■
- 闭合公式推导
将 a(n) 拆分:
a(n)=k=0∑nk−k=0∑ns2(k)=2n(n+1)−S(n)
其中 S(n)=∑k=0ns2(k)。
计算 S(n): 利用按位分解。
s2(k)=j=0∑Lbj(k)
其中 bj(k) 是 k 的第 j 位。交换求和:
S(n)=j=0∑Lk=0∑nbj(k)=j=0∑Lf(n,j)
这里 f(n,j)=∑k=0nbj(k) 表示 [0,n] 中第 j 位为 1 的整数个数。
引理: 在 0,1,2,… 中,第 j 位按周期 2j+1 循环:先 2j 个 0,再 2j 个 1。设 n+1=q⋅2j+1+r(其中 0≤r<2j+1),则:
f(n,j)=q⋅2j+max(r−2j, 0)
证明: 在完整的 q 个周期中,每个周期贡献 2j 个 1。剩余的 r 个数中,前 2j 个的第 j 位为 0,之后的(若有)为 1,贡献 max(r−2j,0)。■
因此最终:
a(n)=2n(n+1)−j=0∑⌊log2n⌋[⌊2j+1n+1⌋⋅2j+max!((n+1)mod2j+1−2j, 0)]
- 验证 Python 代码的等价性
Python 代码:
def A174605(n):
return (n*(n+1)>>1) - (n+1)n.bit_count() - (
sum((m:=1<<j) * ((k:=n>>j) - (r if n<<1 >= m(r:=k<<1|1) else 0))
for j in range(1, n.bit_length()+1)) >> 1)
其中 n*(n+1)>>1 即 2n(n+1),n.bit_count() 即 s2(n)。
代码将 S(n) 分成两部分处理,利用了以下恒等式:
S(n)=(n+1)⋅s2(n)+21j=1∑L2j⋅(⌊2jn⌋−ϵj)
其中 ϵj 是修正项(对应代码中的 r if n<<1 >= m*r else 0),用于处理不完整周期中的余项。这本质上是对上述 f(n,j) 求和公式的代数变形,将完整周期部分与余项部分分离并化简。■
总结: 所有公式的数学根基是 Legendre 公式 ν2(n!)=n−s2(n) 与 二进制位按周期分布 的组合计数。不同代码实现只是对同一求和式的不同代数化简。