0

0

Willans 公式实现中的大数溢出问题与高效修正方案

心靈之曲

心靈之曲

发布时间:2025-12-27 17:48:08

|

591人浏览过

|

来源于php中文网

原创

Willans 公式实现中的大数溢出问题与高效修正方案

本文解析基于 willans 公式的 python 素数生成器为何在计算第 8 个素数时触发 `overflowerror`,并提供数学原理驱动的数值稳定修正方法,避免阶乘转浮点导致的精度崩溃。

Willans 公式是一类利用三角函数和阶乘构造的“闭式”素数判定公式,其核心思想是:对正整数 $ j $,表达式
$$ \left\lfloor \cos^2\left(\pi \cdot \frac{(j-1)! + 1}{j}\right) \right\rfloor $$
当且仅当 $ j $ 为素数时值为 1(由威尔逊定理保证:$ j $ 是素数 ⇔ $ (j-1)! \equiv -1 \pmod{j} $,即 $ \frac{(j-1)!+1}{j} \in \mathbb{Z} $,故余弦值为 $ \cos(k\pi) = \pm 1 $,平方后为 1);否则该值为 0。因此内层求和 sum 实际统计的是区间 $[1, i]$ 内的素数个数 $ \pi(i) $。

但原始代码存在致命数值缺陷:

  • factorial(j-1) 对 $ j \geq 20 $ 已达 $ 10^{18 }$ 量级,而 math.cos() 要求输入为 float,Python 中 int → float 转换在整数超过 $ 2^{53} $(约 $ 9 \times 10^{15} $)时丢失精度;
  • 更严重的是,factorial(7!) = 5040!(当 j=5041 时出现)是一个拥有上万位的整数,远超 float 表示范围,直接触发 OverflowError。

关键误区在于:我们并不需要精确计算 $ \cos\left(\pi \cdot \frac{(j-1)! + 1}{j}\right) $ 的浮点值,而只需判断其是否等于 $ \pm 1 $ —— 这等价于判断 $ \frac{(j-1)! + 1}{j} $ 是否为整数。因此,应彻底规避浮点运算,改用模运算验证威尔逊条件

小艺
小艺

华为公司推出的AI智能助手

下载
def is_prime_wilson(j):
    if j < 2:
        return False
    if j == 2:
        return True
    if j % 2 == 0:
        return False
    # 使用威尔逊定理:j 是素数 ⇔ (j-1)! ≡ -1 (mod j)
    # 但直接算 (j-1)! mod j 仍可能慢;对小 j 可接受,大 j 建议换 Miller-Rabin
    prod = 1
    for k in range(2, j):
        prod = (prod * k) % j
    return prod == j - 1  # 即 (j-1)! ≡ -1 mod j

def nth_prime(n):
    if not isinstance(n, int) or n <= 0:
        raise ValueError("n must be a positive integer")

    count = 0
    candidate = 2
    while count < n:
        if is_prime_wilson(candidate):
            count += 1
            if count == n:
                return candidate
        candidate += 1
    return candidate
✅ 优势:完全整数运算,无浮点溢出风险;逻辑清晰,可验证性高。 ⚠️ 注意:is_prime_wilson 时间复杂度为 $ O(j^2) $,仅适用于教学或极小 $ n $(如 $ n \leq 20 $)。实际应用中应替换为 sympy.isprime() 或 Miller-Rabin 概率素性测试。

若坚持使用 Willans 公式框架(例如用于理论演示),可借助 decimal 模块控制精度,但仍无法解决阶乘过大导致的内存与性能瓶颈。更务实的做法是:承认 Willans 公式在计算数学中具有理论趣味性,但无实用价值——它用高复杂度换取了“公式化”表象,反而掩盖了素数分布的本质计算难度。

总结:OverflowError 根源是误将数论判定问题强行映射到浮点三角函数,违背了数值稳定性原则。正确路径是回归数论本质——用模运算替代浮点余弦,用算法思维替代公式幻觉。

热门AI工具

更多
DeepSeek
DeepSeek

幻方量化公司旗下的开源大模型平台

豆包大模型
豆包大模型

字节跳动自主研发的一系列大型语言模型

通义千问
通义千问

阿里巴巴推出的全能AI助手

腾讯元宝
腾讯元宝

腾讯混元平台推出的AI助手

文心一言
文心一言

文心一言是百度开发的AI聊天机器人,通过对话可以生成各种形式的内容。

讯飞写作
讯飞写作

基于讯飞星火大模型的AI写作工具,可以快速生成新闻稿件、品宣文案、工作总结、心得体会等各种文文稿

即梦AI
即梦AI

一站式AI创作平台,免费AI图片和视频生成。

ChatGPT
ChatGPT

最最强大的AI聊天机器人程序,ChatGPT不单是聊天机器人,还能进行撰写邮件、视频脚本、文案、翻译、代码等任务。

相关专题

更多
css中float用法
css中float用法

css中float属性允许元素脱离文档流并沿其父元素边缘排列,用于创建并排列、对齐文本图像、浮动菜单边栏和重叠元素。想了解更多float的相关内容,可以阅读本专题下面的文章。

594

2024.04.28

C++中int、float和double的区别
C++中int、float和double的区别

本专题整合了c++中int和double的区别,阅读专题下面的文章了解更多详细内容。

105

2025.10.23

python如何计算数的阶乘
python如何计算数的阶乘

方法:1、使用循环;2、使用递归;3、使用math模块;4、使用reduce函数。更多详细python如何计算数的阶乘的内容,可以阅读下面的文章。

177

2023.11.13

python求阶乘教程大全
python求阶乘教程大全

本专题整合了python求阶乘相关教程,阅读专题下面的文章了解更多详细内容。

13

2025.11.08

python语言求阶乘
python语言求阶乘

本专题整合了python中阶乘相关教程,阅读专题下面的文章了解更多详细步骤。

43

2025.12.06

string转int
string转int

在编程中,我们经常会遇到需要将字符串(str)转换为整数(int)的情况。这可能是因为我们需要对字符串进行数值计算,或者需要将用户输入的字符串转换为整数进行处理。php中文网给大家带来了相关的教程以及文章,欢迎大家前来学习阅读。

970

2023.08.02

int占多少字节
int占多少字节

int占4个字节,意味着一个int变量可以存储范围在-2,147,483,648到2,147,483,647之间的整数值,在某些情况下也可能是2个字节或8个字节,int是一种常用的数据类型,用于表示整数,需要根据具体情况选择合适的数据类型,以确保程序的正确性和性能。本专题为大家提供相关的文章、下载、课程内容,供大家免费下载体验。

605

2024.08.29

c++怎么把double转成int
c++怎么把double转成int

本专题整合了 c++ double相关教程,阅读专题下面的文章了解更多详细内容。

294

2025.08.29

JavaScript浏览器渲染机制与前端性能优化实践
JavaScript浏览器渲染机制与前端性能优化实践

本专题围绕 JavaScript 在浏览器中的执行与渲染机制展开,系统讲解 DOM 构建、CSSOM 解析、重排与重绘原理,以及关键渲染路径优化方法。内容涵盖事件循环机制、异步任务调度、资源加载优化、代码拆分与懒加载等性能优化策略。通过真实前端项目案例,帮助开发者理解浏览器底层工作原理,并掌握提升网页加载速度与交互体验的实用技巧。

23

2026.03.06

热门下载

更多
网站特效
/
网站源码
/
网站素材
/
前端模板

精品课程

更多
相关推荐
/
热门推荐
/
最新课程
最新Python教程 从入门到精通
最新Python教程 从入门到精通

共4课时 | 22.5万人学习

Django 教程
Django 教程

共28课时 | 4.8万人学习

SciPy 教程
SciPy 教程

共10课时 | 1.8万人学习

关于我们 免责申明 举报中心 意见反馈 讲师合作 广告合作 最新更新
php中文网:公益在线php培训,帮助PHP学习者快速成长!
关注服务号 技术交流群
PHP中文网订阅号
每天精选资源文章推送

Copyright 2014-2026 https://www.php.cn/ All Rights Reserved | php.cn | 湘ICP备2023035733号