Why Do We Actually Need Private or Protected Inheritance in C++

Why do we actually need Private or Protected inheritance in C++?

It is useful when you want to have access to some members of the base class, but without exposing them in your class interface. Private inheritance can also be seen as some kind of composition: the C++ faq-lite gives the following example to illustrate this statement

class Engine {
public:
Engine(int numCylinders);
void start(); // Starts this Engine
};

class Car {
public:
Car() : e_(8) { } // Initializes this Car with 8 cylinders
void start() { e_.start(); } // Start this Car by starting its Engine
private:
Engine e_; // Car has-a Engine
};

To obtain the same semantic, you could also write the car Class as follow:

class Car : private Engine {    // Car has-a Engine
public:
Car() : Engine(8) { } // Initializes this Car with 8 cylinders
using Engine::start; // Start this Car by starting its Engine
};

However, this way of doing has several disadvantages:

  • your intent is much less clear
  • it can lead to abusive multiple inheritance
  • it breaks the encapsulation of the Engine class since you can access its protected members
  • you're allowed to override Engine virtual methods, which is something you don't want if your aim is a simple composition

C++ why use public, private or protected inheritance?

Use public inheritance to reflect an is-a relationship. This is the main use for inheritance, especially in combination with virtual functions. It allows re-use of interface, not just of old code by new code, but also re-use of new code by old code! (because of virtual function dispatch at runtime).

In exceptional circumstances, use private inheritance to reflect an is-implemented-in-terms-of relationship. This is a commonly overused pattern, often the equivalent goal can be reached through composition (having the would-be base class as a data member). Another drawback is that you can easily have multiple inheritance of the same base class (twice or more removed) leading to the so-called Diamond Problem.

Avoid using protected inheritance, it suggest that your class interface is client-dependent (derived classes versus the world). Often this is due to classes having multiple responsiblities, suggesting a refactoring into separate classes is appropriate.

What is the difference between public, private, and protected inheritance in C++?

To answer that question, I'd like to describe member's accessors first in my own words. If you already know this, skip to the heading "next:".

There are three accessors that I'm aware of: public, protected and private.

Let:

class Base {
public:
int publicMember;
protected:
int protectedMember;
private:
int privateMember;
};
  • Everything that is aware of Base is also aware that Base contains publicMember.
  • Only the children (and their children) are aware that Base contains protectedMember.
  • No one but Base is aware of privateMember.

By "is aware of", I mean "acknowledge the existence of, and thus be able to access".

next:

The same happens with public, private and protected inheritance. Let's consider a class Base and a class Child that inherits from Base.

  • If the inheritance is public, everything that is aware of Base and Child is also aware that Child inherits from Base.
  • If the inheritance is protected, only Child, and its children, are aware that they inherit from Base.
  • If the inheritance is private, no one other than Child is aware of the inheritance.

What is the practical use of protected inheritance?

Private inheritance is also easy but pointless

A : private B means A is implemented by B. However, that's pointless because that means A should contain B instead. Ownership means less coupling with no disadvantage.

That you might not see reasons for private inheritance does not mean it's pointless.
There are several cases where private inheritance has it's reasons. You are right in that at a first glance, private inheritance means has-a relationships just like aggregation, and that private inheritance has a (slightly) tighter coupling.

Reasons for favouring private inheritance over aggretations could be some of the following:

  • With private inheritance you inherit typedefs as well. In some cases (e.g. traits classes) inheriting privatly is just the alternative to re-typedef tons of typedefs in the base class.
  • In seldom cases you have to initialize a member before a "real" (i.e. public) base class. The only way to achieve that is by making that member a private base class inherited before the public base.
  • Some times you need access to protected members of a member. If you can't change the member class itself, you have to use private inheritance to get access to them.
  • If a member has no data members of its own, it still occupies space. Making it a private base class enables the empty base class optimization, diminuishing the size of your class' objects.
  • for even more points, see James' comments below

These reasons are obviously technical reasons, some might even say "hacks". However, such reasons exist, so private inheritance is not completely pointless. It is just not "pure OO style" - but C++ isn't a pure OO language either.

The reason for protected inheritance are quite simple once you understood the ones for private inheritance:

If you have reasons to inherit something privately and want to make those benefits (i.e. that would-be member of your class or the typedefs) accessible to derived classes, use protected inheritance. Obviously, private inheritance should be used scarcely, and protected inheritance even more so.

When should I use C++ private inheritance?

Note after answer acceptance: This is NOT a complete answer. Read other answers like here (conceptually) and here (both theoretic and practic) if you are interested in the question. This is just a fancy trick that can be achieved with private inheritance. While it is fancy it is not the answer to the question.

Besides the basic usage of just private inheritance shown in the C++ FAQ (linked in other's comments) you can use a combination of private and virtual inheritance to seal a class (in .NET terminology) or to make a class final (in Java terminology). This is not a common use, but anyway I found it interesting:

class ClassSealer {
private:
friend class Sealed;
ClassSealer() {}
};
class Sealed : private virtual ClassSealer
{
// ...
};
class FailsToDerive : public Sealed
{
// Cannot be instantiated
};

Sealed can be instantiated. It derives from ClassSealer and can call the private constructor directly as it is a friend.

FailsToDerive won't compile as it must call the ClassSealer constructor directly (virtual inheritance requirement), but it cannot as it is private in the Sealed class and in this case FailsToDerive is not a friend of ClassSealer.


EDIT

It was mentioned in the comments that this could not be made generic at the time using CRTP. The C++11 standard removes that limitation by providing a different syntax to befriend template arguments:

template <typename T>
class Seal {
friend T; // not: friend class T!!!
Seal() {}
};
class Sealed : private virtual Seal<Sealed> // ...

Of course this is all moot, since C++11 provides a final contextual keyword for exactly this purpose:

class Sealed final // ...

why doesnt the support of public or private or protected Inheritance not give in c#

Maybe this is a comment, but its too big to fit in the comment area.

I took your class definitions and tried this out -

class A
{
public:
int pub1;
private:
int prvt1;
protected:
int proc1;
};

class B : public A
{

//public int pub1;//This variable is because of inheritacne and is internal.
//public int proc1;//This variable is because of inheritacne and is internal.
public:
int pub2;
private:
int prvt2;
protected:
int pro2;
};

int main()
{
B* b = new B();
b->pub2 = 1;
b->proc1 = 2;
}

The compiler barked at me -

prog.cpp: In function ‘int main()’:
prog.cpp:8:9: error: ‘int A::proc1’ is protected
prog.cpp:29:8: error: within this context

I guess C++ doesn't convert protected member into public. Or am I missing something from the question?

How to use Private Inheritance aka C++ in C# and Why not it is present in C#

Now, Is there a way to create a HAS-A relationship between C# classes which is one of the thing that I would like to know - HOW?

Make one class have a field of the other class:

class Car
{
Engine engine;
}

A car has an engine.

Another curious question is why doesn't C# support the private (and also protected) inheritance ?

You have a box in your basement. You have never once put anything into it. Someone asks you "why is this box empty?" What answer can you possibly give other than that the box is empty because no one ever put anything into it?

C# doesn't support private or protected inheritance because no one ever implemented that feature and shipped it to customers. Features are not implemented by default, for free. It's not like we started C# with private and protected inheritance and then took them out for some good reason. Those features were never there in the first place, and unsurprisingly, they are still not there. Features don't grow themselves.

Is not supporting multiple implementation inheritance a valid reason or any other?

I don't understand the question.

Is private (and protected) inheritance planned for future versions of C#?

No.

Will supporting the private (and protected) inheritance in C# make it a better language than it is now?

I don't think so.

One of the many problems with inheritance as we typically see it in OOP is that it utterly conflates the "is a kind of" semantic relationship with the "reuses implementation details of" mechanism relationship. Private inheritance partially addresses this problem.

There are a small number of situations in which I would have really liked to have private inheritance in C#; a recent example was that I had a data structure which was possible to construct generally, but which I did not want to expose to users:

internal class FancyDataStructure<T> {...}

but only possible to serialize when T was int (for reasons which are not germane to the discussion.) I would have liked to say:

public class SerializableThingy : private FancyDataStructure<int>

Instead I just made FancyDataStructure<T> a nested type of SerializableThingy and used composition rather than inheritance. There was a small amount of "plumbing" code to write but it worked out just fine.

I don't think adding the feature pays for itself; it adds complexity to the language in exchange for a very small benefit of avoiding some trivial plumbing taxes.

Would supporting the private (and protected) inheritance in C# make it a more widely used language than it is now?

How could I, or anyone else for that matter, possibly know the answer to that question? StackOverflow is a bad place to ask questions that require a prediction of the future based on a counterfactual. My suggestions:

  • Implement a version of C# with the feature you want. See if it becomes popular. Then you'll know.
  • Find someone with psychic powers who can predict how the future would be if things were different now. Since predictions based on counterfactuals are automatically true by the rules of deductive logic, the predictions will be accurate.

What is the difference between private and protected members of C++ classes?

Private members are only accessible within the class defining them.

Protected members are accessible in the class that defines them and in classes that inherit from that class.

Edit: Both are also accessible by friends of their class, and in the case of protected members, by friends of their derived classes.

Edit 2: Use whatever makes sense in the context of your problem. You should try to make members private whenever you can to reduce coupling and protect the implementation of the base class, but if that's not possible then use protected members. Check C++ FAQ for a better understanding of the issue. This question about protected variables might also help.

What is private inheritance, and what issues(s) does it address?

The private inheritance models "is-implemented-in-terms-of". The meaning is similar to "has-a". The differences are:

  1. With private inheritance you don't need to write a wrapper (good for lazy programmers)

  2. "has-a" allows you better control, you can expose only a subset of the interface or change method names if you like.

  3. Private inheritance makes exception safety difficult, have a look at exceptional c++ for more information

  4. You really need private inheritance just when you want to use a protected members of your base class.

  5. Sometimes private inheritance is used in the mix-in class (Effective c++ memory management chapters)

My personal preference is using "has-a" for general purpose, I use private inheritance just after I have rule out other options.



Related Topics



Leave a reply



Submit