在Daniel Solow的“如何阅读和做证明”一书中,我提出了以下问题:
任何整数n> = 2都可以表示为素数的有限乘积。
在看完书中的归纳证明之后,我尝试实施一种算法来验证它:
from fermat import fermat
def first_prime_divisor(n, j):
if not fermat(j):
return first_prime_divisor(n, j+1)
else:
if n%j:
return first_prime_divisor(n, j+1)
else:
return j
def products(n, lista):
if n == 2:
lista.append(2)
elif fermat(n):
lista.append(n)
else:
num = first_prime_divisor(n, 2)
lista.append(num)
products(n//num, lista)
fermat是已知的素性测试。代码工作正常并相应地更改输入列表的状态。 但有两个问题:
1)我不希望有一个列表变量而是函数本身将它返回给我
2)代码不适用于大数(不是很大,例如1531351254251),因为它首先耗尽内存。
你能给出解决它的建议吗?
PS:我试图改进推理的推理方式,所以我已经解决了使用它的问题。
答案 0 :(得分:0)
要删除列表,只需将其设置为内嵌结构:
def products(n):
if n == 2 or fermat(n):
return [n]
else:
num = first_prime_divisor(n, 2)
return products(n//num) + [num]
从这里开始,主要问题是你的递归效率低下;你通过K-1调用找到一个主要的除数K来吹你的堆栈空间。 而是从 n (最近找到的素数)到sqrt(num)运行检查;在该点之后的剩余数字是最终的素数。
然而,最重要的是,你需要打破对递归的依赖,通过除数进行迭代。您的系统堆栈可能不会被设置为处理大约一百万个递归调用的顺序,这是您在寻找10 ^ 12左右的素数时仍然需要的。