3

Consider following code:

class A {
public:
  virtual void f() const = 0;
  void callf() const { f(); }
};

class B : public A {
  virtual void f() const { }
};

int main()
{
  B x;
  x.callf();

  return 0;
}

Class B derives from the abstract base class A, but "hides" the implemented method f() as private member. Still, the inherited member callf() is able to call f(), which was public in the base class. The code compiles with no warning on g++ 10.1.0 and clang++ 11.1.0.

Is this a legal code, i.e., does the inherited callf() correctly see the private member f()?

Alternatively, would it be possible for the derived class B to implement the purely virtual methods of the base class, such that they can only be called by B (and friends)?

francesco
  • 7,189
  • 7
  • 22
  • 49
  • You want a function of derived class not allowed to be called by base? Isn't it breaking Liskov Substitution Principle? – Louis Go Jul 19 '21 at 09:37
  • Not sure what your last sentence/question means. In the code you show, the derived class `B` **does** implement the pure virtual method of the base class. – Adrian Mole Jul 19 '21 at 09:38
  • My suggestion is enforcing the base class fully abstract (deleted), so behavior is defined by derived classes. – Louis Go Jul 19 '21 at 09:39
  • @LouisGo yes, I would like the base class methods to not be able to call f(). – francesco Jul 19 '21 at 09:44
  • Then how does `B::f()` knows whether it's called by base or derived class? Or you want compiler error when `B::f()` is called? – Louis Go Jul 19 '21 at 09:47
  • If you just wants no one uses `B::f()`, [this](https://stackoverflow.com/a/24610165/4123703) might help. – Louis Go Jul 19 '21 at 09:48
  • 1
    Another [answer](https://stackoverflow.com/a/24609999/4123703) for the same question might help as well. – Louis Go Jul 19 '21 at 09:50

1 Answers1

1

Is this a legal code, i.e., does the inherited callf() correctly see the private member f()?

Yes, it is legal code. From the compiler's point-of-view, the callf function is referencing the f function of its own class; the fact that that is a virtual function does not affect the scope (or accessibility) – only the implementation, which will be in the form of a call to a v-table entry. That v-table entry will be correctly interpreted at run time, when it is called via the derived class.

Adrian Mole
  • 49,934
  • 160
  • 51
  • 83