1

私は2^1000のすべての数字を追加するプロジェクトオイラーのプログラムに取り組んでいます。これまでのところ、プログラムのセグメンテーション違反が約5桁に達したときに追跡し、関数carry()の61行目のベクトルに1をプッシュしようとしています。

#include <iostream>
#include <vector>
#include <string>
using namespace std;

class MegaNumber
{
        vector<int> data; //carries an array of numbers under ten, would be char but for simplicity's sake
        void multiplyAssign(int operand, int index); //the recursive function called by the *= operator
        void carry(int index);//if one of the data entries becomes more than ten call this function
    public:
        void printNumber(); //does what it says on the can
        void operator*=(MegaNumber operand);
        void operator*=(int operand);
        void operator+=(int operand);
        MegaNumber(string);
        unsigned long int AddAllDigits();//returns the value of all of the digits summed
};

MegaNumber::MegaNumber(string operand)
{
    for(int i= operand.size()-1; i>=0;i--) //run it into the memory smallest digit first
    {
        data.push_back(operand[i]-48); //converts a text char to an int
    }
}

void MegaNumber::printNumber()
{
    int temp = data.size();
    for(unsigned int i=(temp); i>0;--i)
    {
     cout << (int)data[i-1];
    }
}

void MegaNumber::operator*=(int operand)
{
    if(operand > 9)
    {
        cout << "function does not yet deal with large ints than 9";
    }
    else multiplyAssign(operand, 0);
}

void MegaNumber::multiplyAssign(int operand, int index)
{
    data[index] *=operand;
    if(index<data.size()) multiplyAssign(operand, index+1);
    if(data[index] > 9) carry(index);
}

void MegaNumber::carry(int index)
{

    int temp = (data[index] / 10); //calculate the amount to carry
    if(data.size()==index+1)
    {
     data.push_back(temp);//if there is no upper digit push it onto the stack
    }
    else
    {
        data[index+1]+=temp; //else add it to the next digit

        if(data[index+1]>9) carry(index+1); //rinse and repeat
    }
     data[index]-=temp*10; //remove what's been carried
}

unsigned long int MegaNumber::AddAllDigits() //does what it says on the can
{
    unsigned long int Dagger = 0;
    for(int i=0; i<data.size();i++) Dagger+=data[i];
    return Dagger;
}

int main()
{
    MegaNumber A("2");
    A.printNumber();
    cout << "\n";
    for(unsigned int i=0; i<20; i++) A*=2;
    A.printNumber();
    cout << "\n";
    cout << A.AddAllDigits() << "\n";
    cout << "Hello world!" << endl;
    return 0;
}

これを引き起こしているのは何ですか?

4

3 に答える 3

3

有効なインデックスであるかどうかを確認する前に、data[index]を使用しますmultiplyAssign

data[index] *= operand;
if(index<data.size()) multiplyAssign(operand, index+1);

また、'0'の代わりに使用し48ます。これは、より簡単で、明確で、バグが発生しにくいものです。

于 2009-11-19T20:44:44.237 に答える
2
void MegaNumber::multiplyAssign(int operand, int index)
{
    data[index] *=operand;
    if(index<data.size()) multiplyAssign(operand, index+1);
    if(data[index] > 9) carry(index);
}

indexは0ベースですが、data.size()は1ベースです。data.size()つまり、有効な最大値よりも大きい1を返しますindex。だからあなたの意図があったように見えます

if( index < data.size() - 1) multiplyAssign(operand, index+1);

その後、それは動作します。
PSはあなたのコードを行に分割します、あなたのコードを維持しなければならない人は誰でもそれをあなたに感謝します:

if (index < data.size() - 1) 
{
    multiplyAssign(operand, index + 1);
}
于 2009-11-19T21:06:47.143 に答える
1

問題はここにあると思います:data[index+1]+=temp;

indexパラメータeqの場合、この要素は存在できませんでした。のサイズにdata

だから、私の推奨事項:

  • イテレータを使用してアクセスするstd::vector
  • イテレータを使用しない場合は、境界条件を確認してください
于 2009-11-19T20:51:11.853 に答える