Python 为什么当我尝试记忆时,我的代码会变慢?

Python 为什么当我尝试记忆时,我的代码会变慢?,python,primes,memoization,Python,Primes,Memoization,我有一个函数,它列出了小于N的素数: def ListPrimes(N): list = [2] for n in range(3, N, 2): for i in range(3, int(sqrt(n)+1)): if n % i == 0: break else: list.append(n) return list 我试图加快速度,因此我将一行更改为以

我有一个函数,它列出了小于N的素数:

def ListPrimes(N):
    list = [2]
    for n in range(3, N, 2):
        for i in range(3, int(sqrt(n)+1)):
            if n % i == 0:
                break
        else:
            list.append(n)
    return list
我试图加快速度,因此我将一行更改为以下内容:

def ListPrimesFaster(N):
   list = [2]
   for n in range(3, N, 2):
        for i in list:
            if n % i == 0:
                break
        else:
            list.append(n)
    return list
我感到惊讶的是,第二个版本的速度至少慢了5倍,因为它与第一个版本相同,只是变量我必须遍历一个较短的列表

我正在试图找到一种列出比某些N小的素数的更快方法。

ListPrimesFaster()
不会搜索较短的列表,因为它在
list
中包含高于
sqrt(N)
的元素。
list
的大小比
sqrt(n)
增长得更快,从3开始的范围也节省了一些步骤
ListPrimes(100)
执行
139
n%i==0
测试,而
ListPrimesFaster(100)
执行
362
。当
N
500
时,测试计数为
1616
4933

顺便说一句,在
ListPrimes()
中,内部循环只需要测试奇数因子,因为
n
总是奇数,所以您可以将其更改为:

for i in range(3, int(sqrt(n)+1), 2):

这个简单的改变将
N=100
的测试次数降低到
87
,将
N=500
的测试次数降低到
907
N=500

的速度要快得多,方法是对Eratosthenesh进行筛选。顺便说一句,你到底执行了什么测量?@barakmanos,缩进是正确的,第二个代码段功能正确,阿尔比特慢一点。@KevinW:嗯,我一定是错过了什么。如果
这个其他对应什么?@barakmanos是的,谢谢。我真傻,真不敢相信我错过了!我添加了一个条件,当我达到一个大于sqrt(n)的数字时退出循环,现在它运行得更快了。