Passing reference to derived class object to base class constructor

J

Jeff

The derived class below passes a reference to an object in its own
class to its base calss constructor. The code compiles and will run
successfully as long as the base class constructor does not attempt to
access the object -- since m_object is not actually created and
initizialized until after the base constructor has been called.

Any thoughts on the practice below?
class Base
{
public:
Base(Object& ref) {};
~Base() {};
};

class Derived : public Base
{
public:
Derived(int param) : Base(m_object), m_object(param) {};

protected:
Object m_object;
};
 
V

Victor Bazarov

Jeff said:
The derived class below passes a reference to an object in its own
class to its base calss constructor. The code compiles and will run
successfully as long as the base class constructor does not attempt to
access the object -- since m_object is not actually created and
initizialized until after the base constructor has been called.

Any thoughts on the practice below?

Bad practice. Whoever comes later to do something with 'Base' is not
aware that 'ref' cannot be used during construction. There are some
situations (like if 'Base' as a member of type 'Object&' that cannot
be set later, and has to be initialised) in which you have to pass the
reference to the c-tor, but those cases need to be _extensively_
documented in the code.

On the second thought, it's possible that by redesigning one could work
around this... Need to be dealt with on the case-by-case basis.
class Base
{
public:
Base(Object& ref) {};
~Base() {};

The semicolons after function bodies are unnecessary. And they really
make the code look unclean.
};

class Derived : public Base
{
public:
Derived(int param) : Base(m_object), m_object(param) {};

protected:
Object m_object;
};

V
 
F

Fei Liu

Jeff said:
The derived class below passes a reference to an object in its own
class to its base calss constructor. The code compiles and will run
successfully as long as the base class constructor does not attempt to
access the object -- since m_object is not actually created and
initizialized until after the base constructor has been called.

Any thoughts on the practice below?
class Base
{
public:
Base(Object& ref) {};
~Base() {};
};

class Derived : public Base
{
public:
Derived(int param) : Base(m_object), m_object(param) {};

protected:
Object m_object;
};

The standard requires base class initialized before derived class
member object initialization. Therefore your code will crash if base
constructor access m_object because m_object is not initialized yet.
 
V

Victor Bazarov

Fei said:
Jeff said:
The derived class below passes a reference to an object in its own
class to its base calss constructor. The code compiles and will run
successfully as long as the base class constructor does not attempt to ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
access the object -- since m_object is not actually created and ^^^^^^^^^^^^^^^^^
initizialized until after the base constructor has been called.

Any thoughts on the practice below?
[...]
The standard requires base class initialized before derived class
member object initialization. Therefore your code will crash if base
constructor access m_object because m_object is not initialized yet.

So, if A precedes B, then B must be following A. Did I get it right?
 
P

Peter_Julian

| The derived class below passes a reference to an object in its own
| class to its base calss constructor. The code compiles and will run
| successfully as long as the base class constructor does not attempt to
| access the object -- since m_object is not actually created and
| initizialized until after the base constructor has been called.
|
| Any thoughts on the practice below?
| class Base
| {
| public:
| Base(Object& ref) {};
| ~Base() {};
| };
|
| class Derived : public Base
| {
| public:
| Derived(int param) : Base(m_object), m_object(param) {};
|
| protected:
| Object m_object;
| };
|

If the base class needs a reference to a derived class's component, then
thats a clear sign that that component should be in the base class instead.

class Object { };

class Base
{
Object m_object;
public:
Base(Object o) : m_object(o) { }
virtual ~Base() = 0 { }
virtual Object getObject() const = 0 { return m_object; }
};

class Derived : public Base
{
public:
Derived(Object o) : Base(o) { }
~Derived() { }
/* required pure-virtual interface */
Object getObject() const { return Base::getObject(); }
};

int main()
{
Object obj;
// Base b(obj); cannot instantiate abstract class
Derived d(obj);

return 0;
}
____
hmm, good candidate(s) for a template.

template< class T >
class Base
{
T m_t;
public:
Base(T t) : m_t(t) { }
virtual ~Base() = 0 { }
virtual T getT() const = 0 { return m_t; }
};

template< class T >
class Derived : public Base< T >
{
public:
Derived(T t) : Base(t) { }
~Derived() { }
/* required pure-virtual interface */
T getT() const { return Base::getT(); }
};

class Object { };
class Object2 { };

int main()
{
Object obj;
Derived< Object > d(obj);

Object2 obj2;
Derived< Object2 > d2(obj2);

return 0;
}
 

Ask a Question

Want to reply to this thread or ask your own question?

You'll need to choose a username for the site, which only take a couple of moments. After that, you can post your question and our members will help you out.

Ask a Question

Members online

No members online now.

Forum statistics

Threads
473,744
Messages
2,569,484
Members
44,903
Latest member
orderPeak8CBDGummies

Latest Threads

Top