Home > database >  Exception thrown: read access violation. **this** was 0xCCCCCCCC
Exception thrown: read access violation. **this** was 0xCCCCCCCC

Time:11-05

I'm trying to build an understanding of objects, arrays, and pointers. When I compile my code I ended up with 0xCCCCCCCC. I understand that this error is probably due to an uninitialized pointer. The problem is I don't know where or how to.

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

class Person {
public:
  string name;
};

void createPerson(Person* person[]);


int main() {

  Person* person[5];
  createPerson(person);

  for (int i = 0; i < 5; i  ) {
    cout << person[i]->name << endl;
  }

  return 0;
}

void createPerson(Person* person[]) {
  string n[5] = { "Dwayne Johnson", "Connor McGregor", "SpongeBob","BatMan", "Ash Ketchum" };

  for (int i = 0; i < 5; i  ) {
    person[i]->name = n[1];
  }
}

I'm trying to get the list of names to display.

CodePudding user response:

The Problem is you have an Array of Person Person* person[] pointers and not an array of persons. I fixed the code and removed the pointers:

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

class Person {
public:
  string name;
};

void createPerson(Person person[]);


int main() {

  Person person[5];
  createPerson(person);

  for (int i = 0; i < 5; i  ) {
    cout << person[i].name << endl;
  }

  return 0;
}

void createPerson(Person person[]) {
  string n[5] = { "Dwayne Johnson", "Connor McGregor", "SpongeBob","BatMan", "Ash Ketchum" };

  for (int i = 0; i < 5; i  ) {
    person[i].name = n[i];
  }
}

As you can see I removed the pointer from your array definitions. This way the Person object gets initialized on the stack. In your way the pointers get initialized, but they dont point to anything. Thats why you get your error, because the pointers are dangling. If you really want to use an array of pointer you have to initialize these pointers like this:

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

class Person {
public:
  string name;
};

void createPerson(Person* person[]);


int main() {

  Person* person[5];
  createPerson(person);

  for (int i = 0; i < 5; i  ) {
    cout << person[i]->name << endl;
    
    //delete person so that we dont leak mem
    delete person[i];
  }

  return 0;
}

void createPerson(Person* person[]) {
  string n[5] = { "Dwayne Johnson", "Connor McGregor", "SpongeBob","BatMan", "Ash Ketchum" };

  for (int i = 0; i < 5; i  ) {
    person[i] = new Person();
    person[i]->name = n[i];
  }
}

BTW: I would not use pointers this way. If you are new and try to understand stuff its fine to experiment. But you should almost always use smart_pointers like std::shared_ptr etc. The next thing to experiment with should be containers and proper data structures.

CodePudding user response:

You are declaring an array of pointers of Person, but not initializing those pointers. By default, a pointer can point to some random location based on what garbage value is stored in its respective address (in this case 0xCCCCCCCC).

Solution is simple, just allocate a new memory using new keyword.

Also, since you are using new to allocate memory, you should call delete to de-allocate memory when you no longer require those pointers.

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

class Person {
public:
  string name;
};

void createPerson(Person* person[]);


int main() {

  Person* person[5];
  createPerson(person);

  for (int i = 0; i < 5; i  ) {
    if (person[i] != nullptr)
        cout << person[i]->name << endl;
  }

  for (int i = 0; i < 5; i  ) {
      if (person[i] != nullptr)
          delete person[i];
  }
  return 0;
}

void createPerson(Person* person[]) {
  string n[5] = { "Dwayne Johnson", "Connor McGregor", "SpongeBob","BatMan", "Ash Ketchum" };

  for (int i = 0; i < 5; i  ) {
    person[i] = new Person();
    person[i]->name = n[i];
  }
}

In C , you can use smart pointers instead of raw pointers also. See this

  • Related