Paul
Paul

Reputation: 37

Char* not retaining text inside my class - initialization constructor problem?

I have the following class (I've trimmed irrelevant stuff):

class Example
{
    private:
        char* name;
        int value[4];
        int numVals;
    public:
        Example();
        Example(char name[], int numVals, int, int, int, int);
        ~Example();
};

And here is the initialization constructor:

Example::Example(char na[], int vals, int v1, int v2, int v3, int v4)
{
    name = new char[strlen(na)+1];
    strcpy(name, na);
    numVals = vals;
    value[0] = v1;
    value[1] = v2;
    value[2] = v3;
    value[3] = v4;
    // cout << name; // this DOES print out the correct text

}

In my main(), I have an array of Example class, Example myArray[numRecs]. I then have a loop that uses the initialization constructor to fill the array:

myArray[i] = Example(name, numVals, v[0], v[1], v[2], v[3]);

Everything works as expected, however the name does not retain the characters I put into it. I checked using cout what the value is when it is passed into the constructor, and it was correct! However when I use my Example::Print(), it spits out a random character (the same character for each instance of Example).

Here is the Example::Print()

void Example::Print()
{
    int total, avg;
    total = avg = 0;

    cout << left << setw(20) << name << '\t';

    for(int i=0; i<4; i++){
        if(i<numVals){
            cout << left << setw(8) << value[i];
            total += value[i];
        } else
            cout << left << setw(8) << " ";
    }
    avg = total/numVals;
    cout << left << setw(8) << total <<
        left << setw(8) << avg << endl;
}

Any ideas? Thanks!

Oh and also, this is for an assignment. We have been told to keep the name field as a char pointer, not a string. I am confused as to what I should be using for the init constructor (char* name or char name[] or.. is there a difference?)

EDIT: Here is the destructor and default constructor. I do not have a copy constructor yet as the assignment does not call for it and it is not used. I'll go ahead and make one for completeness anyway.

Example::~Example()
{
    delete [] name;
}

Example::Example()
{
    numVals = 0;
    for(int i=0; i<4; i++)
        value[i] = -1;

}

Upvotes: 1

Views: 363

Answers (2)

user736399
user736399

Reputation:

An easy fix would be to store pointers to the Examples in the array instead of the actual objects. This way, you don't have to deal with copying (which you haven't implemented).

Upvotes: 0

Kerrek SB
Kerrek SB

Reputation: 477522

You should run your program through a memory debugger to witness the nightmare you've created!

You are using manual memory management in your class, yet you forgot to obey the Rule of Three: You didn't implement the copy constructor, assignment operator and destructor! Thus the temporary does allocate memory, copies the pointer (shallowly), and then probably invalidates the memory when it goes out of scope.

The immediate "fix my code" answer is that you have to implement a proper assignment operator and copy constructor to make a deep copy of the char array.

The "this is C++" answer is not to use pointers, new and arrays, and instead std::string.

Upvotes: 2

Related Questions