Question

While I've seen rare cases where private inheritance was needed, I've never encountered a case where protected inheritance is needed. Does someone have an example?

Was it helpful?

Solution

People here seem to mistake Protected class inheritance and Protected methods.

FWIW, I've never seen anyone use protected class inheritance, and if I remember correctly I think Stroustrup even considered the "protected" level to be a mistake in c++. There's precious little you cannot do if you remove that protection level and only rely on public and private.

OTHER TIPS

There is a very rare use case of protected inheritance. It is where you want to make use of covariance:

struct base { 
    virtual ~base() {} 
    virtual base & getBase() = 0;
}; 

struct d1 : private /* protected */ base { 
    virtual base & getBase() { 
        return this; 
    } 
}; 

struct d2 : private /* protected */ d1 {
    virtual d1 & getBase () { 
        return this; 
    } 
}; 

The previous snippet tried to hide it's base class, and provide controlled visibility of bases and their functions, for whatever reason, by providing a "getBase" function.

However, it will fail in struct d2, since d2 does not know that d1 is derived from base. Thus, covariance will not work. A way out of this is deriving them protected, so that the inheritance is visible in d2.

A similar example of using this is when you derive from std::ostream, but don't want random people to write into your stream. You can provide a virtual getStream function that returns std::ostream&. That function could do some preparing of the stream for the next operation. For example putting certain manipulators in.

std::ostream& d2::getStream() {
    this->width(10);
    return *this;
}

logger.getStream() << "we are padded";

C++ FAQ Lite mentions of a case where using private inheritance is a legitimate solution (See [24.3.] Which should I prefer: composition or private inheritance?). It's when you want to call the derived class from within a private base class through a virtual function (in this case derivedFunction()):

class SomeImplementationClass
{
protected:
    void service() {
        derivedFunction();
    }

    virtual void derivedFunction() = 0;      

    // virtual destructor etc
};

class Derived : private SomeImplementationClass
{
    void someFunction() {
        service();
    }

    virtual void derivedFunction() {
        // ...
    }

    // ...
};

Now if you want to derive from the class Derived, and you want to use Base::service() from within the derived class (say you want to move Derived::someFunction() to the derived class), the easiest way to accomplish this is to change the private inheritance of Base to protected inheritance.

Sorry, can't think of a more concrete example. Personally I like to make all inheritance public so as to avoid wasting time with "should I make inheritance relation protected or private" discussions.

Licensed under: CC-BY-SA with attribution
Not affiliated with StackOverflow
scroll top