Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Inserting Objects into an array with dynamic memory (No vectors allowed) C++

I am not allowed to use Vectors specifically for this school assignment. Most of the answers I've found simply state "you should use vectors" as the most up-voted comment. While I appreciate and understand this, I'm simply restricted from using them for this assignment.

It is a C++ assignment with dynamic memory management as follows:

// property in header declaration
int numAnimals;
int capacity;
Animal** animals; 
void addAnimal(Animal *newAnimal);

// class implementation
capacity = 10;
numAnimals = 0;

animals = new Animal*[capacity];

void SampleClass::addAnimal(Animal *newAnimal)
{
  for (int i = 0; i < capacity; i++){
       if(animals[i]){
          // animal object already exists in array, move on
          i++;
       }else{
          animals[i] = newAnimal;
          numAnimals++;
          break;
       }
   }
}

animals is a pointer to a pointer, in this case a pointer to an array of pointers to object type Animal which have yet to be created.

With the 'addAnimal' function, what I'm trying to do is add an animal object to the array by looping through the array of pointers, and if there already exists an animal object, iterate to the next index. If there is no animal, then insert that animal into the array.

I'm getting an exception thrown "read access violation" when I attempt to access a member function of an animal object in the array.

My suspicion is because: if(animals[i]) probably isn't doing what I think it's doing, running it through the debugger I never hit the 'else' portion, so the array is still full of pointers not set to any objects when the method is complete. Therefore, when I try to access a member function, it's of an object that doesn't exist.

So, if my suspicions are correct, then what is the best way to insert a new object into an array of pointers in this fashion? They need to be pointers otherwise it automatically creates the array full of populated objects, which is not what I want.

I didn't post all of the code because I wanted to keep my problem brief, apologies I'm a new to C++ and stackoverflow in general. Yes, I know to delete[] to clear memory afterwards.

Any help is appreciated, thanks!

like image 722
Matthew S Avatar asked Dec 13 '22 20:12

Matthew S


1 Answers

Since in numAnimals you keep count of the current number of animal pointers in the array, you don't need the for loop to find the first available slot to add a new animal pointer (note also that, assuming you want to use a for loop like shown in your code, you have to pay attention to properly initialize all the initial pointers in the array to nullptr).

You can just use:

// Inside SampleClass::addAnimal(Animal *newAnimal):

animals[numAnimals] = newAnimal;
numAnimals++;

Please note that you have to pay attention to not overflow your array capacity, when you insert a new animal.
So, before inserting a new animal, you have to check that there's enough room in the array, e.g.:

// Before inserting:
if (numAnimals == capacity) 
{
    // You ran out of capacity.
    //
    // 1. Allocate a new array with bigger capacity (e.g. 2X)
    // 2. Copy the content from the current array to the new one
    // 3. delete current array
}

As a side note:

Yes, I know to delete[] to clear memory afterwards

Note that if you call delete[] on the animals array of pointers, you release this pointer array, but not the Animal objects pointed to.

like image 111
Mr.C64 Avatar answered Apr 27 '23 00:04

Mr.C64