Cody Smith
Cody Smith

Reputation: 2732

C++ Member variables confusion

I'm learning C++ (coming from Java) and this is bugging the hell out of me, say I have...

class Foo {

public:

    Bar &x; // <- This is a ref, Bar is not instantiated (this is just a placeholder)
    Bar *y; // <- This is a pointer, Bar is not instantiated (this is just another placeholder)
    Bar z;  // <- What is this???

};

class Bar {

public:

    Bar(int bunchOfCrap, int thatNeedsToBeHere, double toMakeABar);

};

In this example Bar has one constructor that needs a bunch of fields specified in order to create a "Bar." Neither x, nor y creates a Bar, I understand that x creates a reference that can be pointed to a Bar and that y creates a pointer that can also represent a Bar.

What I don't understand is what exactly z is.

Thanks!

Upvotes: 0

Views: 277

Answers (4)

Marcelo Cantos
Marcelo Cantos

Reputation: 185862

z is an instance of Bar, and must be constructed when Foo is, thus:

class Foo {
public:
    Foo(…)
        : x(<instance of or reference to Bar>),
          y(<pointer to Bar>), // optional
          z(<Bar ctor params>)
    { … }

Note that both x and z must be initialized during construction, whereas it is legal (albeit questionable) to omit y's initialization.

z occupies the same memory as the parent Foo instance, but it is an instance of Bar, not just a Bar-sized chunk of memory.

Upvotes: 1

nneonneo
nneonneo

Reputation: 179432

For pedagogical reasons, let's try to compile this code:

class Bar {
public:
    Bar(int bunchOfCrap, int thatNeedsToBeHere, double toMakeABar);
};

class Foo {
public:
    Bar &x; // <- This is a ref, Bar is not instantiated (this is just a placeholder)
    Bar *y; // <- This is a pointer, Bar is not instantiated (this is just a *safer* placeholder)
    Bar z;  // <- What is this???
};

int main() {
    Foo foo;
}

Output:

c++     uuu.cpp   -o uuu
uuu.cpp:10:7: error: implicit default constructor for 'Foo' must explicitly initialize the reference member 'x'
class Foo {
      ^
uuu.cpp:14:10: note: declared here
    Bar &x; // <- This is a ref, Bar is not instantiated (this is just a placeholder)
         ^
uuu.cpp:10:7: error: implicit default constructor for 'Foo' must explicitly initialize the member 'z' which does not
      have a default constructor
class Foo {
      ^
uuu.cpp:16:9: note: member is declared here
    Bar z;  // <- What is this???
        ^
uuu.cpp:2:7: note: 'Bar' declared here
class Bar {
      ^
uuu.cpp:21:9: note: implicit default constructor for 'Foo' first required here
    Foo foo;
        ^
2 errors generated.
make: *** [uuu] Error 1

As it says, you must initialize both the member reference Bar &x and the member variable Bar z;, because Bar doesn't have a default constructor. y doesn't have to be initialized, and it will default to NULL.

Both x and y indirectly refer to the object. You can't change what x refers to (so it must be initialized when Foo is instantiated). You can change what y refers to. z is a Bar-sized chunk of memory which lives inside Foo; for you to legally declare a member variable like this, you have to put the complete definition of Bar before Foo so that the compiler knows how big Bar is.

Upvotes: 3

billz
billz

Reputation: 45410

Is it a Bar? And if so, how can it be given Bar's only constructor?

Yes, z is a bar. If Bar has no default constructor you have to initialize Bar in Foo member initializers list. Below sample ignores x, y initialization:

Foo::Foo(int param1, int param2, int param3)
: z(param1, param2, param3)
{
}

Is it a Bar sized chunk of memory belonging to instances of Foo that can be initialized into a Bar?

Yes, Bar object is aligned inside Foo object

Upvotes: 1

Chris Dargis
Chris Dargis

Reputation: 6043

  1. Yes it is a bar: z is a value identifier of type Bar. This will generate a compiler error if you have not defined a default constructor (the compiler normally does this but it won't if you have defined at least one construction -> which you have).
  2. Yes it is a Bar sized chunk of memory, allocated when Foo is allocated.

Upvotes: 1

Related Questions