鱼C论坛

 找回密码
 立即注册
查看: 2576|回复: 8

[已解决]new project euler 第三题

[复制链接]
发表于 2023-7-3 00:43:16 | 显示全部楼层 |阅读模式

马上注册,结交更多好友,享用更多功能^_^

您需要 登录 才可以下载或查看,没有账号?立即注册

x
https://fishc.com.cn/thread-228243-1-1.html

  1. def getyinshus(n):
  2.     return [i for i in range(2, int(n ** 0.5) + 1) if n % i == 0]

  3. def isprime(n):
  4.     return len(getyinshus(n)) < 3

  5. def getprimeyinshus(n):
  6.     return [i for i in getyinshus(n) if isprime(i)]

  7. print(max(getprimeyinshus(600851475143)))
  8. #486847
复制代码


难道是我数学没学好吗……
最佳答案
2023-7-3 07:23:08
原因可能出在getyinshus和isprime上。getinshus函数判断的范围是0,n**0.5(向上取整),但是质因数不一定都小于n**0.5,比如14=2*7,7>14**0.5。
getyinshus返回的并不是n所有的因数,因此isprime调用getyinshus函数判断质数会出错。比如getyinshus(14)返回[1,2],isprime就会认为14是个质数
小甲鱼最新课程 -> https://ilovefishc.com
回复

使用道具 举报

发表于 2023-7-3 07:23:08 From FishC Mobile | 显示全部楼层    本楼为最佳答案   
原因可能出在getyinshus和isprime上。getinshus函数判断的范围是0,n**0.5(向上取整),但是质因数不一定都小于n**0.5,比如14=2*7,7>14**0.5。
getyinshus返回的并不是n所有的因数,因此isprime调用getyinshus函数判断质数会出错。比如getyinshus(14)返回[1,2],isprime就会认为14是个质数
小甲鱼最新课程 -> https://ilovefishc.com
回复 支持 反对

使用道具 举报

 楼主| 发表于 2023-7-3 09:11:06 | 显示全部楼层
smallwh 发表于 2023-7-3 07:23
原因可能出在getyinshus和isprime上。getinshus函数判断的范围是0,n**0.5(向上取整),但是质因数不一定都小 ...

看完答案后进行了更改,这样对了吗
  1. def isprime(n):
  2.     for i in range(2, int(n ** 0.5) + 1):
  3.         if n % i == 0:
  4.             return False
  5.     return True

  6. def getprimeyinshus(n):
  7.     return [i for i in range(2, int(n ** 0.5) + 1) if n % i == 0 and isprime(i)]

  8. print(max(getprimeyinshus(600851475143)))
复制代码
小甲鱼最新课程 -> https://ilovefishc.com
回复 支持 反对

使用道具 举报

发表于 2023-7-3 12:56:19 | 显示全部楼层
本帖最后由 smallwh 于 2023-7-3 13:07 编辑

不对。在 getprimeyinshus 中,i 取值范围还是0,n**0.5(向上取整),会导致分解的因数不全。
14=1*2*7,7是14的最大质因数。但在你的程序中,getprimeyinshus返回值是 [1,2]。很明显,7被遗漏了。

若要避免遗漏,i 应满足1<i<=n(若n为质数,则n为n的最大质因数,所以要取n),但会导致程序运行时间长
可以使用分解质因数来代替寻找所有因数再判断是否为质数,代码如下
  1. def fenjiezhiyinshu(n):
  2.     if n <= 3:
  3.         return n
  4.     elif n % 2 == 0:
  5.         return fenjiezhiyinshu(n//2)
  6.     else:
  7.         for i in range(3,n,2):
  8.             if n % i == 0:
  9.                 return fenjiezhiyinshu(n//i)
  10.             elif i >= int(n**0.5) + 1:
  11.                 return n
复制代码

求72的质因数,我们通常可以这么做:
72÷2=36,36÷2=18,18÷2=9,9÷3=3
因此,72的最大质因数是3。这一段代码的原理与其类似,通过不断除以因数来求最大的质因数
小甲鱼最新课程 -> https://ilovefishc.com
回复 支持 反对

使用道具 举报

 楼主| 发表于 2023-7-3 12:58:30 | 显示全部楼层
smallwh 发表于 2023-7-3 12:56
不对。在 getprimeyinshus 中,i 取值范围还是0,n**0.5(向上取整),会导致分解的因数不全。
14=1*2*7,7是 ...

谢谢,你看看 3# 的对不对
小甲鱼最新课程 -> https://ilovefishc.com
回复 支持 反对

使用道具 举报

发表于 2023-7-3 13:02:04 | 显示全部楼层
将600851475143换成14,就会返回2,3#的方法不一定对所有数字都有效
小甲鱼最新课程 -> https://ilovefishc.com
回复 支持 反对

使用道具 举报

发表于 2023-7-3 13:03:16 | 显示全部楼层
本帖最后由 smallwh 于 2023-7-3 13:07 编辑
smallwh 发表于 2023-7-3 12:56
不对。在 getprimeyinshus 中,i 取值范围还是0,n**0.5(向上取整),会导致分解的因数不全。
14=1*2*7,7是 ...


错误改完了
小甲鱼最新课程 -> https://ilovefishc.com
回复 支持 反对

使用道具 举报

 楼主| 发表于 2023-7-3 13:03:50 | 显示全部楼层
smallwh 发表于 2023-7-3 13:02
将600851475143换成14,就会返回2,3#的方法不一定对所有数字都有效

所以问题出在哪
小甲鱼最新课程 -> https://ilovefishc.com
回复 支持 反对

使用道具 举报

发表于 2023-7-3 13:09:07 | 显示全部楼层
  1.     return [i for i in range(2, int(n ** 0.5) + 1) if n % i == 0 and isprime(i)]
复制代码

int(n ** 0.5) + 1改为n+1就是正确的,但这样对大数太慢了
小甲鱼最新课程 -> https://ilovefishc.com
回复 支持 反对

使用道具 举报

您需要登录后才可以回帖 登录 | 立即注册

本版积分规则

小黑屋|手机版|Archiver|鱼C工作室 ( 粤ICP备18085999号-1 | 粤公网安备 44051102000585号)

GMT+8, 2025-6-27 19:23

Powered by Discuz! X3.4

© 2001-2023 Discuz! Team.

快速回复 返回顶部 返回列表