【问题标题】:Trying to solve the Biggest Prime Factor problem from Project Euler (Problem 3) through recursion in python试图通过python中的递归解决Project Euler(问题3)中的最大素数问题
【发布时间】:2020-05-22 14:37:21
【问题描述】:

我一直在尝试在 python 中解决 ProjectEuler 中的问题 #3。我尝试使用递归来获取我的因子的因子。但是由于某种原因,我不断遇到递归限制达到错误。谁能帮我看看为什么会这样?

def getPrimeFactors(y):
  AllFactors = [[x, int(y/x)] for x in range(1, (int(math.sqrt(y)+1))) if y%x==0]
  Flattened_AF = [j for i in AllFactors for j in i]
  print(AllFactors)
  print(Flattened_AF)

  if len(Flattened_AF)==2:
    print(Flattened_AF)
    return Flattened_AF
  else:
    PrimeFactors = [x for x in Flattened_AF if len(getPrimeFactors(x))==2]
    print (f'loop in else - {PrimeFactors}')
    print(max(PrimeFactors)

getPrimeFactors(4)

这是网站中引用的problem

如果代码可读性质量有点低,我很抱歉,但我尝试调试了很长时间都没有成功。

【问题讨论】:

  • [x, int(y/x)] for x in range(1, (int(math.sqrt(y)+1))) if y%x==0 中,通过测试的第一个最小的x 保证是素数。无需测试。然后,不需要找到所有的质因数,只需要找到最大的一个。为此,保持 迄今为止最大的已知 就足够了。你认为你免费获得了int(y/x),但这是错误的经济,因为它不能保证是素数,它的素数也不能保证是原始的最大的。最后,为什么在 Python 中使用递归?为什么不循环?
  • 我之前在 Project Euler 上做过这个问题。您会发现使用递归或 for 循环会起作用,但计算机需要很长时间才能计算出答案。 (如果我没记错的话,我想我用 for 循环计算这个答案大约需要一个小时,如果你使用递归,它会花费更长的时间)。有一个公式可以以一种超级有效的方式解决这个问题,但这不是你自己想出来的。你要么知道,要么不知道。它被称为埃拉托色尼筛。
  • @WillNess 最初的想法是我会识别某个数字的所有因子直到它的平方根,因为之后它会重复它的因子对(y/x)以提高代码效率大数字。然后我会检查每个原始因子的因子列表的长度,看看它是否是素数(长度为 2)。因此初始化为 1。至于递归,经过更多调试后,我现在可以看到它只是将自己挖到一个洞中并且本质上不会工作,所以我决定定义另一个函数来检查素数。
  • @wp-overwatch.com 是的.. 我最初尝试使用 for 循环和简单的蛮力但不会像你说的那样工作所以我尝试了另一种我描述的方法我上面的回复涉及将平方根设置为此处提到的上限。 link。我一定会检查一下埃拉托色尼筛。
  • @WillNess 知道了!我不敢相信质因数分解没有足够早地打击我。有了这个和平方根规则,找到一个像 septillion 这样大的数字的因子只需不到一分钟的时间。感谢您的推动!

标签: python recursion primes


【解决方案1】:

当您在输入 y 中定义 AllFactors 时,您从 1 开始迭代,因此相同的数字 y 始终包含在 AllFactors 中。因此,当您在输入上调用 getPrimeFactors 时,会传递相同的输入 y,因此这变成了一个无限循环。

从 2 而不是 1 迭代停止递归错误。

另外,只是一个提示,通常在 python 中,变量名称以小写字母开头,类以大写字母开头。这里有更多关于命名约定的内容:https://visualgit.readthedocs.io/en/latest/pages/naming_convention.html

【讨论】:

  • 从两个迭代确实停止了递归错误,并且还向我展示了我的方法必须解决这个问题的逻辑错误。通过不必要地挖掘因素,它最终得到一个空集。我决定使用外部函数而不是递归来检查素数。感谢您的回答和提示!
  • 不用担心,在这种情况下,您可以将此答案标记为正确!祝你好运。
猜你喜欢
  • 2023-02-13
  • 2010-09-27
  • 2019-09-29
  • 1970-01-01
  • 2010-09-17
  • 2010-11-06
  • 2022-11-29
  • 1970-01-01
  • 2019-07-26
相关资源
最近更新 更多