python - 如何改进此代码以提高时间效率?For循环,素数
问题描述
该任务来自www.codewars.com
素数不是规则间隔的。例如,从 2 到 3,步长为 1。从 3 到 5,步长为 2。从 7 到 11,步长为 4。在 2 到 50 之间,我们有以下成对的 2 步素数:
3, 5 - 5, 7, - 11, 13, - 17, 19, - 29, 31, - 41, 43
我们将编写一个带参数的函数步骤:
g (integer >= 2) 表示我们正在寻找的步骤,
m (integer >= 2) 给出搜索的开始(包括 m),
n (integer >= m) 结束搜索(n 包括在内)
在上面的示例中, step(2, 2, 50) 将返回 [3, 5] ,它是 2 到 50 之间的第一对,有 2 步。
所以这个函数应该返回两个素数中的第一对,在限制 m 之间间隔 g 步长,如果这些 g 步长素数存在,则 n 否则为 nil 或 null 或 None 或 Nothing 或 [] 或 "0, 0"或 {0, 0} 或 0 0(取决于语言)。
示例:step(2, 5, 7) --> [5, 7] or (5, 7) or {5, 7} or "5 7"
step(2, 5, 5) --> nil or ... or [] in Ocaml or {0, 0} in C++
step(4, 130, 200) --> [163, 167] 或 (163, 167) 或 {163, 167}
在“测试”中查看您的语言的更多示例
备注:([193, 197] 也是 130 到 200 之间的这样一个 4 步素数,但它不是第一对)。
step(6, 100, 110) --> [101, 107] 虽然在 101 和 107 之间有一个素数,即 103;101-103 对是 2 步。
这是我的解决方案,它运行良好,并且比测试所需的更多,但是,我正在尝试优化此代码以使其更省时。
def step(g,m,n):
count = 0
list= []
list2 = []
for num in range(m,n+1):
if all(num%i!=0 for i in range(2,num)):
count += 1
list.append(num)
for k in list:
for q in list:
if (q-k) > 0:
if (q-k) == g:
list2.append(k)
list2.append(q)
if not list2:
return
else:
return [list2[0],list2[1]]
如果您有任何建议甚至示例代码,我将不胜感激。
解决方案
首先,永远不要使用关键字作为变量。
要采用更好的方法,您需要考虑方法中的缺陷。
- 您正在遍历所有数字以确定素数。
- 您正在遍历 O(n**2) 中的列表以查找是否存在具有所需差异的对。
- 您的素数计算算法不是最佳的。
对于第一点,甚至不需要找到给定范围内的所有素数,因为您的任务是找到具有所需差异的第一对。因此,如果您发现数字
a
既是素数a + g
又是素数,那么您已经找到了解决方案。
对于第二点,您可以简单地遍历列表,并检查if (k + g) in list
是否找到了该对。
对于第三点,您可以在 wikipedia 页面本身上找到最佳实现。如果你能理解逻辑,那么你可以很容易地自己编写那个实现。
因此,将最佳素数检查实现与单个循环迭代相结合,可以轻松编写解决方案,如下所示。
from functools import lru_cache
@lru_cache(None)
def is_prime(n):
if n <= 3:
return n > 1
if n % 2 == 0 or n % 3 == 0:
return False
i = 5
while i ** i <= n:
if n % i == 0 or n % (i + 2) == 0:
return False
i += 6
return True
def step(g, m, n):
for i in range(m, n + 1 - g):
if is_prime(i) and is_prime(i + g):
return [i, i + g]
return
对于step(4, 130, 200)
. 如您所见,一旦实现该is_prime
功能,逻辑就非常简单。
推荐阅读
- matrix - 如何在排序的 MxN 矩阵中找到第 K 个最小的和
- mysql - 在没有无效使用组的情况下计算 mysql
- performance - 如何加速这个 python 循环脚本或并行化它
- typescript - 我怎样才能让 TypeScript 相信我从这个链中得到了 [number, number] ?
- flask - 如何将使用 SQLAlchemy 创建的数据库导入 Flask 应用程序?
- c# - 通常要求呼叫者通过队列进行通信?
- c# - 具有数组结构的 JSON
- java - 错误:不兼容的类型:org.opencv.core.Point 无法转换为 android.graphics.Point
- processing - 如何多次迭代同一个草图-(处理)
- python - Pandas - 读取文本文件