2

I am at a loss as to why I cannot

  1. Declare an object pointer set to 0
  2. Pass the object pointer to a function that will create the object
  3. The function sets the passed pointer to the newly allocated object

Example

#include <iostream>

using namespace std;

class Unit {
  public:
  Unit();
  ~Unit();
  string name;
};

Unit::Unit(){}
Unit::~Unit(){}

void DoFoo(Unit *unit);

int main()
{
    Unit *unit = 0;
    DoFoo(unit);
    cout << unit->name;

    return 0;
}

void DoFoo(Unit *unit){
    unit = new Unit();
    unit->name = "hi";
}

Result is Segment fault...

In my head I am simply declaring a pointer, passing the address to the function, and then the function is setting the address to the address of the allocated object...

ICU_
  • 159
  • 1
  • 8
  • 5
    Because there's nothing special about pointers. It's exactly the same as `void foo(int x) { x = 12; } int main() { int y = 0; foo(y); /* y is still 0 */}`. – molbdnilo Aug 07 '18 at 13:17
  • 1
    unless really needed, I would choose to return the pointer. – apple apple Aug 07 '18 at 13:20
  • 3
    Or return an object - thereby avoiding pointers and this kind of trouble – doctorlove Aug 07 '18 at 13:21
  • You did "passing the address to the function" - you pass zero, which gets copied, by value. And then set to something else *inside* the function. Meanwhile, but at the call site... things haven't changed. So `unit->name` is sitll `0->name` i.e. goes bang – doctorlove Aug 07 '18 at 13:25
  • Damn. Was closed while I was writing an answer >:-( – JHBonarius Aug 07 '18 at 13:26
  • 1
    Missing a `delete`-statement. Try using `std::shared_ptr` and `std::unique_ptr` instead of `new`. That's the modern C++ approach. – JHBonarius Aug 07 '18 at 13:27

1 Answers1

4

You pass a copy of the pointer and allocate an object there. Use a references:

void DoFoo(Unit *&unit);

void DoFoo(Unit *&unit){
    unit = new Unit();
    unit->name = "hi";
}
Lex Sergeev
  • 231
  • 1
  • 3
  • 17