triangle numbers in python
我正在努力解决这个问题:
What is the value of the first triangle number to have over five hundred divisors?
号
一个三角形的数字是一个数字序列的总和,即1+2+3+4+5…
我很确定这是有效的代码,但我不知道,因为我的电脑计算时间太长了。有人知道如何使程序更快一点吗?谢谢。
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 | import math def main(): l = [] one = 0 a = 1 b = 2 while one == 0: a = a + b b += 1 for x in range(1, int(a/2 + 1)): if a % x == 0: l.append(x) if len(l) > 499: print a if __name__ == '__main__': main() |
提示:
n 第三角数的公式是什么?n 和n+1 没有共同因素(1 除外)。问题:给定n 和n+1 中的因子个数,如何计算n*(n+1) 中的因子个数?那么,n/2 和(n+1) (或n 和(n+1)/2 呢?- 如果你知道
n 的所有素因子,如何计算n 的除数?
如果你不想改变你的算法,你可以通过:
- 用
factor_count += 1 代替l.append 。 - 枚举
int(a**.5) ,而不是a/2 (在本例中使用factor_count += 2 )。
你必须多思考,少用暴力来解决项目欧拉的问题。
在这种情况下,您应该研究三角形数有哪些除数,有多少除数。从一开始,寻找模式,试着理解问题。
首先,人们告诉你,你不能在一分钟内用暴力解决这个问题,这是错误的。针对这个大小的问题的一个蛮力算法将在几秒钟内运行。
第二,您发布的代码有几个问题,其中一些已经提到。
- 当您达到目标条件(当前的
print a )时,您应该通过将one 设置为0 以外的某个值来终止循环。 - 您永远不能重新初始化列表(
l = [] )。每次重新计算a 和b 时,都应在进入for循环之前执行此操作。 - 这个问题要求第一个三角数有超过500个除数。你方终止合同的条件应为
if len(l) > 500: 。 - 您可能不想在for循环内执行ecx1(22),但要等到while循环完成后再执行。
真正让你慢下来的是,对于每个三角形数
下面是您的代码以及我上面概述的修改:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 | import math def main(): l = [] one = 0 a = 1 b = 2 while one == 0: a = a + b b += 1 l = [] sqrt_a = int(math.sqrt(a)) for x in range(1, sqrt_a + 1): if a % x == 0: l.append(x) if x < math.sqrt(a): l.append(a // x) if len(l) > 500: # print(a) one = 1 print(a, b, len(l)) if __name__ == '__main__': main() |
号
你会看到它在5到6秒的时间内运行,所以经过这些修改后,不到一分钟就可以了。
为了理智,你应该使用
1 | while True: |
把
你没有更新EDOCX1的值(0),所以你的程序永远不会结束。
您当前的蛮力算法效率太低,无法在项目欧拉时间限制1分钟内解决此问题。相反,我建议查看除数函数:
http://www.artofproblemsolving.com/wiki/index.php/divisor_函数