查找具有500个以上因素的数字时遇到的问题

时间:2019-08-21 21:15:41

标签: javascript

这是projecteuler网站上的问题12:

三角形数字的序列是通过将自然数相加而生成的。因此,第7个三角数将是1 + 2 + 3 + 4 + 5 + 6 + 7 =28。前十个项将是:

1、3、6、10、15、21、28、36、45、55,...

让我们列出前七个三角形数字的因数:

 1: 1
 3: 1,3
 6: 1,2,3,6
10: 1,2,5,10
15: 1,3,5,15
21: 1,3,7,21
28: 1,2,4,7,14,28

我们可以看到28是第一个具有超过5个除数的三角形。

第一个具有500个除数的三角形的值是多少?

这是我的代码(我是Java语言的新手)

let num = 1;
let add= 1;
let divisors = [];

while (divisors.length < 500){
  divisors = []

  for(let i = 1; i <= num; i++){
    if(num % i == 0){
      divisors.push(i);
    }
  }

  add ++;
  num += add;
}
console.log(num - add)

当我将while循环条件更改为300或更小时,此代码运行良好。 并且此代码在Intel i7 Q740 1.75GHz上运行。 当我尝试它时,控制台上什么都没有显示,我的问题是由于我的CPU和电源不足或者我的代码有问题?我等了大约20分钟,结果还是一无所获。

3 个答案:

答案 0 :(得分:1)

您可能已经注意到,该算法可能有点蛮力。更好的方法是结合一些东西。假设我们要查找的数字是“ n”:

  1. 查找范围为[1,n的平方根]的所有素数。你会 遍历n,所以sieve of eratosthenes 将有助于提高效率(您可以记住已经找到的素数)
  2. 鉴于可以将任何数字表示为某个幂的质数,再乘以某个幂的质数,等等。您可以找到这些质数与幂的所有组合,它们是{{1}的因数}。

这将是一种更有效率的方法,尽管找到它们的方法更加复杂。您可以查看此法定人数答案以了解更多详细信息:https://www.quora.com/What-is-an-efficient-algorithm-to-find-divisors-of-any-number

答案 1 :(得分:1)

@Vasil Dininski指出,此代码的效率不是很高,但是您将无法达到最大Integer,而只需要等待一段时间才能计算程序即可。

我建议优化您的代码,例如通过编写一个简单的函数,该函数返回您当前数的除数。

这可能看起来像这样:

function numberOfDivisors(num) {
  var numOfDivisors = 0;
  var sqrtOfNum = Math.sqrt(num);

  for(var i = 1; i <= sqrtOfNum; i++) {
    if(num % i == 0) {
      numOfDivisors += 2;
    }
  }
  // if your number is a perfect square you have to reduce it by one
  if(sqrtOfNum * sqrtOfNum == num) {
    numOfDivisors--;
  }
  return numOfDivisors;
}

然后您可以在while循环中使用此方法,如下所示:

var maxNumOfDivisors = 500;
var num = 0;
var i = 1;

while(numberOfDivisors(num) < maxNumOfDivisors) {
  num += i;
  i++;
}

这将为您返回正确的三角数。

请注意,三角形数字从0开始,这就是为什么我的数字为0的原因。

答案 2 :(得分:-1)

如果我的计算没错,则将上一个除数的下一个除数再增加一个,即可得到最终结果。

python