【问题标题】:Understanding the logic of this prime number generator output理解这个素数生成器输出的逻辑
【发布时间】:2021-12-30 19:12:11
【问题描述】:

此代码用于输出给定范围内的素数:

def sqrt(n):
    return n**0.5

# find primes
def primes(minNum, maxNum):
    primes_sum = 0
    for i in range(minNum, maxNum):
        current_max = int(sqrt(i))
        for n in range(2, current_max + 1):
            if(i%n == 0):
                break
            else:
                primes_sum += i
                print(i)
                break
            
    print('\nSum of all primes: ', primes_sum)
        
primes(10, 20)

但是,我得到一个不正确的输出:

11, 13, 15, 17, 19

有人知道 15 是如何出现的吗?我将打印语句放在第一个 if 语句块中,以验证 if(i%n == 0) 条件检测到 15,确实如此,但不知何故,它仍然出现在我的最终输出中,我不知道为什么。

【问题讨论】:

  • 15 出现在素数中,因为您的代码将检查15 是否可以被2sqrt(15)+1 之间的数字整除,即23。但是当它检查 15 是否可以被 2 整除时,如果语句失败,然后它会转到 else 语句并将 15 打印为素数
  • @SAISANTOSHCHIRAG 哦,我现在明白了。我的逻辑缺陷是没有意识到,一旦第一个 if 语句不满足,它就会转移到 else 语句,我不知道在这种情况下我是如何轻易地忽略了这一点。谢谢。
  • 如果我的回答解决了你的问题,你能接受吗?我已经添加了代码。如果您接受将不胜感激

标签: python primes


【解决方案1】:

@SAI SANTOSH CHIRAG 完美解释了原因。我不会复制那个。我不确定你为什么使用 sqrt 的数字。你可以在没有 sqrt 的情况下做这些事情。如果你使用 sqrt,你会得到错误的输出。在您的情况下,如果我们检查 18 的 sqrt,则它的 int 将为 4,并且从 2 到 4 检查可除性,而 18 也可被 6 整除。我正在设计一个没有 sqrt 的新代码并对其进行解释。

我的逻辑:定义一个以上限和下限为参数的函数。取一个从下限到上限的 for 循环。现在每个值都将是范围之间的数字。我们必须检查这个数字是否是素数。使用从 2 到数字的循环,并检查它是否可整除。如果是,它不是素数。如果不是,则将其添加到总和中。你的代码:

def primes(low,upp):
    su=[]
    for i in range(low,upp+1):
        f=True
        for j in range(2,i):
            if i%j==0:
                f=False
        if f:
            su.append(i)
    return su,sum(su)
print(primes(10,20))

【讨论】:

  • sqrt 是为了提高效率,从 2 到 N 的素数,大于 √N 的数不需要检查。
  • 是的,但程序变得冗长。你可以不用 sqrt 来缩短代码行数
【解决方案2】:

我对您的代码进行了更改。试试这样:

def sqrt(n):
    return n**0.5

# find primes
def primes(minNum, maxNum):
    primes_sum = 0
    for i in range(minNum, maxNum):
        current_max = int(sqrt(i))
        #print(current_max)
        flag = True
        for n in range(2, current_max + 1):
            #print(i,n)
            if(i%n == 0):
                flag = False
        if flag:
            print(i)
            primes_sum += i

            
    print('\nSum of all primes: ', primes_sum)
        
primes(10, 200)

在您的代码中,您没有检查所有数字是否可以被所有数字整除。对于所有奇数的非素数,它将失败,因为它将检查它是否可以被 2 整除,如果不是,它是素数

【讨论】:

  • 谢谢。实际上我也已经实现了这个方法,但我真的很想知道为什么另一种方法不起作用,但我现在明白了。
【解决方案3】:

这个逻辑:

        for n in range(2, current_max + 1):
            if(i%n == 0):
                break
            else:
                primes_sum += i
                print(i)
                break

无法检测素数,因为如果您测试的n 的第一个值(将为2)不是一个因素,您将立即将其视为素数并中断循环。在确定一个数字是素数之前,您需要完成整个范围的迭代:

        for n in range(2, current_max + 1):
            if i % n == 0:
                break
        else:
            primes_sum += i
            print(i)

请注意elsefor 的一部分,而不是if ——它仅在for 循环耗尽自身而没有碰到break 时执行(即,如果它没有找到任何作为i 因子的n 值。

【讨论】:

  • 你用第一句话就赚了一大笔钱。我不知道我是如何忽略这样一个事实的,即一旦不满足 if 语句,它就会转移到 else 语句。
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2020-08-02
  • 2020-07-06
  • 1970-01-01
  • 1970-01-01
  • 2017-08-05
相关资源
最近更新 更多