Derived class constructor that takes the base class as an argument (is this good practice?)

I have two simple classes below, one base and the other deriving from it.
The derived class has two constructors, one that takes all the arguments required for the base and the derived class, and the other that takes a reference to the base class as an argument.

I know that a constructor that takes a reference to the base class as an argument is not good practice.
However, I was wondering why this is not considered good practice? It achieves the same as the other constructor.

Can someone please clarify why this is not good OOP practice?

class Base
{
public:
    Base(int a, int b):
        m_a(a),
        m_b(b)
    {}

    Base(const Base& b):
        m_a(b.m_a),
        m_b(b.m_b)
    {}

    ~Base() {}

protected:
    int m_a;
    int m_b;
};

class Derived : public Base
{
public:
    // Constructor which takes base class argument and initializes base
    Derived(Base &base, int c):
        Base(base),
        m_c(c)
    {}


    Derived(int a, int b, int c):
        Base(a, b),
        m_c(c)
    {}

    ~Derived() {}

private:
    int m_c;
};

int main()
{
    Base base(1,2);
    Derived derived1(base, 3); //
    Derived derived2(1,2, 3);
}

      

+3


source to share


2 answers


You need to know the context in which you are specifying the first Derived constructor.

However, it might be more elegant to define it with a parameter const Base

. Something like:

Derived(const Base &base, int c):
        Base(base),
        m_c(c)
    {}

      

Thus, it tells the compiler that it is protecting the state of the object base

.

Also, if you are using C ++ - 11, you might be interested in declaring:

using Base::Base;

      



inside a class Derived

, making this one Derived

inheriting from constructors base

. So you can add to yours main()

:

Derived derived3(1,2);

      

and it will compile just fine.

In C ++ - 11, you can also set a default value for a data member m_c

. eg

int m_c = 0;

      

And so the constructor inherited from base

will leave Derived

in a consistent state

0


source


I believe the code you are showing is not bad OOP practice. Users Derived

know and have access to by Base

virtue of Derived

using public inheritance. Because of this, you are not adding any dependencies and therefore are not doing anything more restrictive or complicated.

That said, even if you Derived

used protected or private inheritance, it might not be entirely bad practice depending on whether the users knew Derived

about the class Base

.

Imagine the following:



class Derived { // no inheritance
public:
    void doSomething(const X& b); // `X` could be `Base`, `Foo`, or `std::string` for that matter...
};

      

Would you call this bad practice? I think no. The key here, as in the code you submitted (assuming you added a const specifier to Base & as suggested by lrleon), is what you use Base

as the value type. Derived

does not hold a pointer / reference to the underlying object being passed, so you have normal parameter passing, and there is nothing unusual or bad about parameter passing.

0


source







All Articles