【问题标题】:Syntax error in python code to find Prime-factors. Id appreciate if someone could help me用于查找素数因子的 python 代码中的语法错误。如果有人可以帮助我,我将不胜感激
【发布时间】:2020-10-29 14:57:18
【问题描述】:

我在使用素因数分解的代码时遇到语法错误

这是代码

from sys import argv
from os import system, get_terminal_size
from math import sqrt

number = int(argv[1])
width = get_terminal_size().columns
prime_numbers = []
prime_factors = []
_ = system('clear')
print() 

def is_prime(n):
    for i in range(2, n):
        if n % i == 0:
            return False

    return True

if is_prime(number):
    print(f"It is a prime number \nIts only factors are 1 and itself \n1, {number}")
    exit()

x = len(str(number))
for i in range(2, int(sqrt(number))):
    if is_prime(i):
            prime_numbers.append(i)

            #print(f"found ")
#print(prime_numbers)

i = 0
while True:
    if (number % prime_numbers[i] != 0):
        i += 1
        continue
    
    prime_factors.append(prime_numbers[i])
    print("%2d  | %3d".center(width) % (prime_numbers[i], number))
    print("_________".center(width))                                
    number /= prime_numbers[i]
    if number == 1:
        break
print("1".center(width))

print("Answer ")

i = len(prime_factors)
j = 1

for k in prime_factors:
    if j == i:
        print(k)
        break

    print(f"{k}", end=" X ")
    j += 1

这适用于小于 4 或 5 位的小数字,但对于较大的数字会产生索引错误。 如果我在第 24 行删除 sqrt 函数,它开始花费太长时间。

错误看起来像这样

Traceback (most recent call last):
  File "prime-factor.py", line 33, in <module>
    if (number % prime_numbers[i] != 0):
IndexError: list index out of range

real    0m0.049s
user    0m0.030s
sys 0m0.014s
(base) Souravs-MacBook-Pro-5:Fun-Math-Algorithms aahaans$ time python3 prime-factor.py 145647

我无法解决此问题,如果您能帮助我,我将不胜感激。

【问题讨论】:

  • 我很惊讶您的代码在某些情况下有效。您的prime_factors 被初始化为一个空列表,然后直接在while 循环中的表达式if (number % prime_numbers[i] != 0): 中使用。 prime_numbers[0] 肯定是索引超出范围错误,因为prime_numbers 为空。
  • 您发布的错误不是语法错误。您还可以无条件地增加i 的值,并期望prime_numbers[i] 起作用。

标签: python algorithm


【解决方案1】:

无需重建已有的primePy

from primePy import primes
primes.factors(101463649)

输出

[7, 23, 73, 89, 97]

【讨论】:

    【解决方案2】:

    代码有两个基本问题。对于素数的 for 循环之一,您必须检查直到 int(sqrt(number))+1。并且,在那之后的while循环中,当数字低于原始数字的sqrt时,您必须中断,应该使用另一个变量。更正后的代码是:

    from sys import argv
    from os import system, get_terminal_size
    from math import sqrt
    
    number = int(argv[1])
    width = get_terminal_size().columns
    prime_numbers = []
    prime_factors = []
    _ = system('clear')
    print() 
    
    def is_prime(n):
      for i in range(2, n):
        if n % i == 0:
          return False
    
      return True
    
    if is_prime(number):
      print(f"It is a prime number \nIts only factors are 1 and itself \n1, {number}")
      exit()
    
    x = len(str(number))
    limit = int(sqrt(number))
    for i in range(2, limit+1):
      if is_prime(i):
        prime_numbers.append(i)
    
    i = 0
    while True:
      if i == len(prime_numbers)-1:
        # prime_factors.append(int(number))
        break
      if (number % prime_numbers[i] != 0):
        i += 1
        continue
      prime_factors.append(prime_numbers[i])
      print("%2d  | %3d".center(width) % (prime_numbers[i], number))
      print("_________".center(width))                                
      number /= prime_numbers[i]
    prime_factors.append(int(number))
    print("%2d  | %3d".center(width) % (number, number))
    print("_________".center(width))
    print("1".center(width))
    
    print("Answer ")
    i = len(prime_factors)
    j = 1
    for k in prime_factors:
      if j == i:
        print(k)
        break
      print(f"{k}", end=" X ")
      j += 1
    

    如果我的解释不清楚,请查看代码中的更改。

    【讨论】:

      【解决方案3】:

      我写了一个小数分解引擎,可以分解数字。

      
      import math
      
      def LLL(N):
         p = 1<<N.bit_length()-1
         if N == 2:
           return 2
         if N == 3:
           return 3
         s = 4
         M = pow(p, 2) - 1
         for x in range (1, 100000):
           s = (((s * N ) - 2 )) % M
           xx = [math.gcd(s, N)] + [math.gcd(s*p+x,N) for x in range(7)] + [math.gcd(s*p-x,N) for x in range(1,7)] 
           try:
              prime = min(list(filter(lambda x: x not in set([1]),xx)))
           except:
              prime = 1
           if prime == 1:
              continue
           else:
              break
         #print (s, x, prime, xx)
         return prime
      

      因素:

      In [219]: LLL(10142789312725007)                                                                                                                                                       
      Out[219]: 100711423
      
      from https://stackoverflow.com/questions/4078902/cracking-short-rsa-keys
      

      如果您想在 python 中进行因式分解(超过 60 位级别),我还让 Alpertons ECM SIQs 引擎在 python 中工作:https://github.com/oppressionslayer/primalitytest

      【讨论】:

        猜你喜欢
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 2017-11-28
        • 2017-11-14
        • 2020-05-29
        • 1970-01-01
        • 1970-01-01
        • 2021-05-11
        相关资源
        最近更新 更多