为什么找到包含> 500因素的最小三角形数的程序会崩溃?

时间:2016-09-14 03:12:46

标签: c++ factorization

我编写了下面的程序来解决Project Euler 12,它涉及查找超过500个因子的最小三角形数。

我认为没有重大错误。我怀疑内存优化可能是一个问题。然而,话虽如此,我需要无符号长long int作为最终将成为答案的大三角数。我在triangleNumbers [0] = 10,000,000,000处开始我的自然数序列。我知道9,000,000,000有大约300个因素,所以10,000,000,000是“最好的猜测”。 尽管如此,我认为10,000,000,000是“第一个自然数”并继续添加后续自然数以获得“第二个”自然数以及更多(因此triangleNumbers [1] = 10,000,000,000 + 2,triangleNumbers [2] = 10,000,000,000 +3,等等。)

任何建议和提示将不胜感激。感谢您帮助初学者改进。

#include <iostream>
#include <vector>
#include <math.h>

using namespace std;

bool keepRunning=true;

unsigned long long int naturalNumberCount=0;
unsigned long long int j=4;
unsigned long long int sum=0;

vector <unsigned long long int> triangleNumbers(0);

unsigned long long int totalFactors=0;
unsigned long long int trialDivisors=1;

unsigned long long int storer=0;

int main()
{
    triangleNumbers[0]=10000000000;
    triangleNumbers[1]=10000000002;
    triangleNumbers[2]=10000000005;
    triangleNumbers[3]=10000000009;
    triangleNumbers[4]=10000000014;
    //listed first few prime numbers above. j is set at 4 for this reason

    naturalNumberCount=5;
    //10000000014 is the 5th triangle number, and 5 is the 5th natural num
    //need this for recursive relation
    //5th triangle number = 4th triangle num + 5 (num + naturalNumberCount

    while(keepRunning)
    {
        for(trialDivisors;trialDivisors<=(unsigned long long int)(sqrt(triangleNumbers[j]));trialDivisors++)
        {
            if(triangleNumbers[j]%trialDivisors==0)
            {
                totalFactors++;
                if(totalFactors>499)//499 because the number itself will be a divisor of itself, so no need to check
                {
                    keepRunning=false;
                    break;
                }
                else
                {
                    keepRunning=true;
                }
            }
            else
            {
                keepRunning=true;
            }
        }
        //need the below to generate and store the next triangle number (as next element of array)

        naturalNumberCount++;//for recursive relation
        storer=triangleNumbers[j];//store the (j+1)'th triangle number, since we are changing j itself
        j++;//raise j, we gonna add the next value
        triangleNumbers[j]=(storer+naturalNumberCount);//the new value (last triangle number + current natural)
        totalFactors=0;//reset total factors to preclude any carry-over
    }


    cout<<triangleNumbers[j]<<flush;

    return 0;
}

1 个答案:

答案 0 :(得分:0)

TL;DR

#include <vector>

std::vector <unsigned long long int> triangleNumbers(0);

int main()
{
    triangleNumbers[0]=10000000000;
}

你有一个空向量,main中的第一行会导致未定义的行为,因为你试图访问项目0(没有这样的项目)。

Live Example using operator [ ]

Live Example showing what vector::at() does

注意第二个链接使用at()代替[ ]来访问第一个项目,表明您正在访问一个超出范围的元素。

要将项目添加到std::vector,请使用其中一种方法,即vector::push_back()vector::insert()vector::emplace_back()vector::resize()或用必要数量的条目构造std::vector

所有这些选项中最简单的方法是使用初始化列表构建向量:

std::vector<unsigned long long int> triangleNumbers = {10000000000, 10000000002, 10000000005, 10000000009, 10000000014};

std::vector reference

正确设置向量后,您需要查看其余代码,以查看您可能在何处访问越界索引。特别是在循环中查看j,以及如何将其用作索引。如果vector::at()超出界限,j函数会立即告诉您。

编辑:如果您真的想要一种模拟“自动展开”数组的语法,那么您最接近的就是使用this example所见的std::unordered_map<int, unsigned long long>

map解决方案可能是替代品 - 您必须对其进行测试。