python中的三角形数字

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第三角数的公式是什么?
  • nn+1没有共同因素(1除外)。问题:给定nn+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 = [])。每次重新计算ab时,都应在进入for循环之前执行此操作。
  • 这个问题要求第一个三角数有超过500个除数。你方终止合同的条件应为if len(l) > 500:
  • 您可能不想在for循环内执行ecx1(22),但要等到while循环完成后再执行。

真正让你慢下来的是,对于每个三角形数a,你要检查a / 2之前的每个值,看它是否是除数。您只需要检查到a的平方根的值。这样,对于EDOCX1的每个值(31),如果x是一个除数,您可以将xa / x添加到列表中。

下面是您的代码以及我上面概述的修改:

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:

one除掉。


你没有更新EDOCX1的值(0),所以你的程序永远不会结束。


您当前的蛮力算法效率太低,无法在项目欧拉时间限制1分钟内解决此问题。相反,我建议查看除数函数:

http://www.artofproblemsolving.com/wiki/index.php/divisor_函数