三种解法,效率依次提升:
- 直接法
- 开方后逐个判断法
- 利用公式
1. 直接法
对于给定的数num,直接遍历 (2,num)
之间是否存在它的合数。
num = int(input('请输入一个正整数: '))
is_prime = True
for x in range(2, num):
if num % x == 0:
is_prime = False
break
if is_prime and num != 1:
print('%d是素数' % num)
else:
print('%d不是素数' % num)
2. 初步优化
若所给定的数num
不是素数,那么存在不等于 1 的两个约数x1
和 x2
,并且满足x1 >= sqrt(num)
,x2 <= sqrt(num)
。因此可直接搜索 num % x1
是否为0来判断素数。
from math import sqrt
num = int(input('请输入一个正整数: '))
end = int(sqrt(num))
is_prime = True
for x in range(2, end + 1):
if num % x == 0:
is_prime = False
break
if is_prime and num != 1:
print('%d是素数' % num)
else:
print('%d不是素数' % num)
3. 进一步优化
素数有一个特点,总是满足 num = 6x - 1
或 num = 6x + 1
,其中 x
为自然数且有 x >= 1
。
证明:
6x
肯定不是素数,因为可以被 6 整除;6x + 1
未知;6x + 2
肯定不是素数,可以被 2 整除;6x + 3
肯定不是素数,可以被 3 整除;6x + 4
肯定不是素数,可以被 2 整除;6x + 5
未知, 并且6x + 5
等同于6x - 1
;
因此,对于大于等于 5 的素数,不能表示成 6x - 1
或 6x + 1
的一定不是素数。能表示的部分,有一些不是素数。因此,只需找到不是素数的这部分的就可以了。 因此,在遍历的时候就可以以 6 为步长来进行判断。
from math import sqrt
num = int(input('请输入一个正整数: '))
end = int(sqrt(num))
is_prime = True
if num % 6 != 1 and num % 6 != 5 and num != 3:
is_prime = False
for x in range(5, end+1, 6):
print(x)
if num % x == 0 or num % (x + 2) == 0:
is_prime = False
if is_prime and num != 1:
print('%d是素数' % num)
else:
print('%d不是素数' % num)