algorithm - 计算表达式长度而不计算表达式本身

标签 algorithm math formula

我需要在不计算表达式本身的情况下计算复杂表达式的十进制长度(包含阶乘)。 例如: ( 400!/( 100! * 300!) ) 的十进制长度 任何可以完成任务或数学公式的方法都可能有用。 谢谢。

最佳答案

如果近似值足够,我们可以使用斯特林近似值:

n! ~ sqrt(2×πn)×(n/e)n

这个结果直接对我们的目标来说不是很有趣,但是我们可以使用log10来获取位数:

log10(n!) ~ log10(sqrt(2×πn))+n×log10(n/e )

现在我们可以计算a!/(b!×c!)的位数,使用:

log(a!/(b!×c!)) = log(a!)-log(b!)-log(c!)

等于:

log(a!/(b!×c!)) = log10(sqrt(2×πa))+a×log10(a/e )-log10(sqrt(2×πb))-b×log10(b/e)-log10(sqrt(2 ×πc))-c×log10(c/e)

而一个数n的位数大概是⌊log(n)⌋+1。

例如在 Python 中我们可以近似:

from math import log10, pi, e, sqrt, floor

def approx_fac_log10(n):
    return log10(sqrt(2.0*pi*n))+n*log10(n/e)

def approx_length(a,b,c):
    return 1+floor(approx_fac_log10(a)-approx_fac_log10(b)-approx_fac_log10(c))

对于你的公式,我们得到:

>>> approx_length(400,100,300)
97

如果我们计算结果,我们得到:

>>> factorial(400)//(factorial(100)*factorial(300))
2241854791554337561923210387201698554845411177476295990399942258896013007429693894018935107174320
>>> factorial(400)/(factorial(100)*factorial(300))
2.2418547915543375e+96

如果我们将结果转换为字符串,然后获取该字符串的长度,我们将得到:

>>> len(str(factorial(400)//(factorial(100)*factorial(300))))
97

所以近似值是正确的:结果确实有 97 位。

您可以通过在 Stirling 近似 中使用更多 项来提高近似的质量。最终,如果你采用无限数量的项,你确实会准确地计算出结果:

approximation

关于algorithm - 计算表达式长度而不计算表达式本身,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/45575755/

相关文章:

python - 找到最大化正确多数决定数量的预测子集

java - 从未排序的输入返回唯一值的算法

python - 在 Sympy 中收集类似的表达式

javascript - Math.floor VS Math.trunc JavaScript

Excel:两个范围的标量积

e-commerce - 如何计算给定百分比包含值的原始值?

jquery - DOM 上类似于电子表格的公式

algorithm - 为什么桶排序在输入排序后运行得更快?

algorithm - 对文件进行排序以优化压缩效率

php - 从数组中访问唯一值对而无需重复自己