A virtual function that must be overridden - c++

Consider a base class class Base which has a function virtual void foo(void). This function is implemented in Base; i.e. is not pure virtual.
Is there a pattern I can use which when inheriting from this class, i.e. class Child : public Base, compels me to override foo?

Other than making it a pure virtual function, there is no way to make the override required.
Note that the fact that a function is marked pure virtual does not mean that it cannot have an implementation in the base class - it means only that the derived class must override it.
struct Base {
virtual void foo() = 0; // foo() is pure virtual
};
struct Derived : public Base {
void foo() { // Derived overrides the pure virtual
cout << "Hello ";
Base::foo(); // Call the implementation in the base
cout << endl;
}
};
void Base::foo() {
cout << " world";
}
int main() {
Derived d;
d.foo();
return 0;
}
This prints "Hello world", with the "world" part coming from the implementation in the base class.
Demo.

C++11 introduced the override keyword to help with this:
struct Base
{
void foo();
};
struct Derived : Base
{
void foo() override; // error! Base::foo is not virtual
};
However you can not write this in Base itself to get the same effect; i.e. there is no mustoverride specifier. Ultimately, it is none of Base's business as to what derived classes do or don't override.
You can keep Base abstract whilst providing a "default" definition for your pure virtual functions:
struct Base
{
virtual void foo() = 0;
};
void Base::foo() {}
struct Derived : Base {}; // error! does not override Base::foo
struct Derived2: Base
{
virtual void foo() override
{
Base::foo(); // invokes "default" definition
}
};
This will be an acceptable solution if you are content for the entire base type to be rendered uninstantiable.

A pure-virtual member function can still have a body. The only caveat is that it must be defined outside the class definition. This is perfectly legal C++:
#include <iostream>
struct Base
{
virtual void foo() const = 0;
};
void Base::foo() const
{
std::cout << "Base!\n";
}
struct Derived : Base
{
// Uncomment following line to remove error:
//virtual void foo() const override { std::cout << "Derived\n"; Base::foo(); }
};
int main()
{
Derived d;
d.foo();
}
Live example
Notice that this makes Base an abstract class in all respects, i.e. it's impossible to instantiate Base directly.

Yes, actually there is:
#include <iostream>
class Base
{
public:
virtual void someFun() {std::cout << "Base::fun" << std::endl;}
virtual ~Base() {}
};
class AlmostBase : public Base
{
public:
virtual void someFun() = 0;
};
class Derived : public AlmostBase
{
public:
virtual void someFun() {std::cout << "Derived::fun" << std::endl;}
};
int main()
{
Derived *d = new Derived();
d->someFun();
delete d;
}
If you uncomment the someFun from Derived the compiler will complain ...
You introduce an intermediary class AlmostBase which has the function as pure virtual. This way you can have Base objects too, and the only drawback now is that all your classes will need to inherit from the intermediary base.

you can make the base method throw an exception when called, then the class must override it to avoid the parent execution.
this is used in the MFC FrameWork for example
// Derived class is responsible for implementing these handlers
// for owner/self draw controls (except for the optional DeleteItem)
void CComboBox::DrawItem(LPDRAWITEMSTRUCT)
{ ASSERT(FALSE); }
void CComboBox::MeasureItem(LPMEASUREITEMSTRUCT)
{ ASSERT(FALSE); }
int CComboBox::CompareItem(LPCOMPAREITEMSTRUCT)
{ ASSERT(FALSE); return 0; }
those methods must be inherited if the control is owner drawn it is responsible for the measuer, draw,... if you missed it while you are testing the function you will get an assert or exception with useful information thrown.

Related

Overriding non-virtual function from abstract grandparent class

I am learning and playing around with inheritance and abstract classes. I've run into a predicament that I would appreciate some clarifications on.
I am trying to override a non-virtual function from an abstract grandparent class. I am getting an error saying that 'member function declared with 'override' does not override a base class member.
I can call the original non-virtual function from child class instances in main(), but not override them in child classes?
Here's the code.
UPDATE:
Error went away when I marked the function as virtual, I would still appreciate an explanation as to why that virtual is necessary?
#include <iostream>
using namespace std;
class A
{
public:
virtual string GetClassName() = 0;
void foo(); // <--- this is the problem function
{
cout << "foo" << endl;
}
};
class B : public A
{
public:
string GetClassName() override
{
return "B";
}
};
class C1 : public B
{
public:
string GetClassName() override
{
return "C";
}
};
class C2 : public B
{
public:
void foo() override // ERROR:member function declared with override does not override a base class member.
{
cout << "foo c1" << endl;
}
};
// testing interface
void printName(A* ptr)
{
cout << ptr->GetClassName() << endl;
}
int main()
{
B* b = new B();
C1* c1 = new C1();
C2* c2 = new C2();
printName(b); // prints B
printName(c1); // prints C
printName(c2); // prints B
b->foo(); // prints foo, inherited directly from abstract class
c1->foo(); // prints foo, inherited directly from abstract class
c2->foo(); // ??
}
You cannot override a non-virtual function. It is as simple as that.
Methods in child classes can hide methods of parent classes when they have the same name, for example:
struct A {
void foo(){}
};
struct B : A {
void foo() {}
};
But thats not overriding. To override the method must be virtual. Thats one of the conditions that the override specifier helps to check:
struct A {
virtual void foo(){}
};
struct B : A {
void foo() override {} // <- error if A::foo is not virtual
};
PS: I have seen poor tutorials, that use the first example and call that overriding. Thats just wrong.

Virtual function behavior in derived classes

Can I have a virtual function in the base class and some of my derived classes do have that function and some don't have.
class A{
virtual void Dosomething();
};
class B : public A{
void Dosomething();
};
class C : public A{
//Does not have Dosomething() function.
};
From one of my c++ textbook:
Once a function is declared virtual, it remains virtual all the way down the inheritance, even if the function is not explicitly declared virtual when the derived class overrides it.
When the derived class chooses not to override it, it simply inherits its base class's virtual function.
Therefore to your question the answer is No. Class c will use Class A's virtual function.
Derived classes do not have to implement all the virtual functions, unless it is a pure virtual function. Even in this case, it will cause an error only when you try to instantiate the derived class( without implementing the pure virtual function ).
#include <iostream>
class A{
public :
virtual void foo() = 0;
};
class B: public A{
public :
void foo(){ std::cout << "foo" << std::endl;}
};
class C: public A{
void bar();
};
int main() {
//C temp; The compiler will complain only if this is initialized without
// implementing foo in the derived class C
return 0;
}
I think the closest you might get, is to change the access modifier in the derived class, as depicted below.
But, I would consider it bad practice, as it violates Liskov's substitution principle.
If you have a situation like this, you might need to reconsider your class design.
#include <iostream>
class A {
public:
virtual void doSomething() { std::cout << "A" << std::endl; }
};
class B : public A {
public:
void doSomething() override { std::cout << "B" << std::endl; };
};
class C : public A {
private:
void doSomething() override { std::cout << "C" << std::endl; };
};
int main(int argc, char **args) {
A a;
a.doSomething();
B b;
b.doSomething();
C c;
//c.doSomething(); // Not part of the public interface. Violates Liskov's substitution principle.
A* c2 = &c;
c2->doSomething(); // Still possible, even though it is private! But, C::doSomething() is called!
return 0;
}

Base class method alias

Let's consider the following code:
#include <iostream>
class Base
{
public:
void foo() //Here we have some method called foo.
{
std::cout << "Base::foo()\n";
}
};
class Derived : public Base
{
public:
void foo() //Here we override the Base::foo() with Derived::foo()
{
std::cout << "Derived::foo()\n";
}
};
int main()
{
Base *base1 = new Base;
Derived *der1 = new Derived;
base1->foo(); //Prints "Base::foo()"
der1->foo(); //Prints "Derived::foo()"
}
If I have the above stated classes, I can call the foo method from any of Base or Derived classes instances, depending on what ::foo() I need. But there is some kind of problem: what if I need the Derived class instance, but I do need to call the Base::foo() method from this instance?
The solve of this problem may be next:
I paste the next method to the class Derived
public:
void fooBase()
{
Base::foo();
}
and call Derived::fooBase() when I need Base::foo() method from Derived class instance.
The question is can I do this using using directive with something like this:
using Base::foo=fooBase; //I know this would not compile.
?
der1->Base::foo(); //Prints "Base::foo()"
You can call base class method using scope resolution to specify the function version and resolve the ambiguity which is useful when you don't want to use the default resolution.
Similar (Not exactly same case) example is mentioned # cppreference
struct B { virtual void foo(); };
struct D : B { void foo() override; };
int main()
{
D x;
B& b = x;
b.foo(); // calls D::foo (virtual dispatch)
b.B::foo(); // calls B::foo (static dispatch)
}

Inheriting the virtual specifier of base class's member function

The following code is based on the example on page 298 of C++ Templates: the Complete Guide. I removed the parts not relevant to my question.
class Virtual {
public:
virtual void foo() {
}
};
class Base : private Virtual {
public:
void foo() {
std::cout << "Base::foo()" << '\n';
}
};
class Derived : public Base {
public:
void foo() {
std::cout << "Derived::foo()" << '\n';
}
};
int main()
{
Base *p = new Derived;
p->foo(); // calls Derived::foo()
}
I do not understand how the call p->foo() ends up calling Derived::foo. More concretely, the static type of p is Base*. Base::foo is non-virtual. Now, Base privately inherits from 'Virtual', which has its own foo and it looks as if Base::foo somehow gets the virtual specifier from Virtual::foo. What is actually going on here?
The virtualness of foo is inherited from the base class Virtual.
In fact, writing virtual in Derived::foo will be superfluous and many developers will omit it. You cannot undo virtualness once you've marked that function as virtual in a base class.
You can force a call of Base::foo by writing p->Base::foo(); but that's an ugly contrivance.

Call base class method from derived class object

How can I call a base class method which is overridden by the derived class, from a derived class object?
class Base{
public:
void foo(){cout<<"base";}
};
class Derived:public Base{
public:
void foo(){cout<<"derived";}
}
int main(){
Derived bar;
//call Base::foo() from bar here?
return 0;
}
You can always(*) refer to a base class's function by using a qualified-id:
#include <iostream>
class Base{
public:
void foo(){std::cout<<"base";}
};
class Derived : public Base
{
public:
void foo(){std::cout<<"derived";}
};
int main()
{
Derived bar;
//call Base::foo() from bar here?
bar.Base::foo(); // using a qualified-id
return 0;
}
[Also fixed some typos of the OP.]
(*) Access restrictions still apply, and base classes can be ambiguous.
If Base::foo is not virtual, then Derived::foo does not override Base::foo. Rather, Derived::foo hides Base::foo. The difference can be seen in the following example:
struct Base {
void foo() { std::cout << "Base::foo\n"; }
virtual void bar() { std::cout << "Base::bar\n"; }
};
struct Derived : Base {
void foo() { std::cout << "Derived::foo\n"; }
virtual void bar() { std::cout << "Derived::bar\n"; }
};
int main() {
Derived d;
Base* b = &d;
b->foo(); // calls Base::foo
b->bar(); // calls Derived::bar
}
(Derived::bar is implicitly virtual even if you don't use the virtual keyword, as long as it's signature is compatible to Base::bar.)
A qualified-id is either of the form X :: Y or just :: Y. The part before the :: specifies where we want to look up the identifier Y. In the first form, we look up X, then we look up Y from within X's context. In the second form, we look up Y in the global namespace.
An unqualified-id does not contain a ::, and therefore does not (itself) specify a context where to look up the name.
In an expression b->foo, both b and foo are unqualified-ids. b is looked up in the current context (which in the example above is the main function). We find the local variable Base* b. Because b->foo has the form of a class member access, we look up foo from the context of the type of b (or rather *b). So we look up foo from the context of Base. We will find the member function void foo() declared inside Base, which I'll refer to as Base::foo.
For foo, we're done now, and call Base::foo.
For b->bar, we first find Base::bar, but it is declared virtual. Because it is virtual, we perform a virtual dispatch. This will call the final function overrider in the class hierarchy of the type of the object b points to. Because b points to an object of type Derived, the final overrider is Derived::bar.
When looking up the name foo from Derived's context, we will find Derived::foo. This is why Derived::foo is said to hide Base::foo. Expressions such as d.foo() or, inside a member function of Derived, using simply foo() or this->foo(), will look up from the context of Derived.
When using a qualified-id, we explicitly state the context of where to look up a name. The expression Base::foo states that we want to look up the name foo from the context of Base (it can find functions that Base inherited, for example). Additionally, it disables virtual dispatch.
Therefore, d.Base::foo() will find Base::foo and call it; d.Base::bar() will find Base::bar and call it.
Fun fact: Pure virtual functions can have an implementation. They cannot be called via virtual dispatch, because they need to be overridden. However, you can still call their implementation (if they have one) by using a qualified-id.
#include <iostream>
struct Base {
virtual void foo() = 0;
};
void Base::foo() { std::cout << "look ma, I'm pure virtual!\n"; }
struct Derived : Base {
virtual void foo() { std::cout << "Derived::foo\n"; }
};
int main() {
Derived d;
d.foo(); // calls Derived::foo
d.Base::foo(); // calls Base::foo
}
Note that access-specifiers both of class members and base classes have an influence on whether or not you can use a qualified-id to call a base class's function on an object of a derived type.
For example:
#include <iostream>
struct Base {
public:
void public_fun() { std::cout << "Base::public_fun\n"; }
private:
void private_fun() { std::cout << "Base::private_fun\n"; }
};
struct Public_derived : public Base {
public:
void public_fun() { std::cout << "Public_derived::public_fun\n"; }
void private_fun() { std::cout << "Public_derived::private_fun\n"; }
};
struct Private_derived : private Base {
public:
void public_fun() { std::cout << "Private_derived::public_fun\n"; }
void private_fun() { std::cout << "Private_derived::private_fun\n"; }
};
int main() {
Public_derived p;
p.public_fun(); // allowed, calls Public_derived::public_fun
p.private_fun(); // allowed, calls Public_derived::public_fun
p.Base::public_fun(); // allowed, calls Base::public_fun
p.Base::private_fun(); // NOT allowed, tries to name Base::public_fun
Private_derived r;
r.Base::public_fun(); // NOT allowed, tries to call Base::public_fun
r.Base::private_fun(); // NOT allowed, tries to name Base::private_fun
}
Accessibility is orthogonal to name lookup. So name hiding does not have an influence on it (you can leave out public_fun and private_fun in the derived classes and get the same behaviour and errors for the qualified-id calls).
The error in p.Base::private_fun() is different from the error in r.Base::public_fun() by the way: The first one already fails to refer to the name Base::private_fun (because it's a private name). The second one fails to convert r from Private_derived& to Base& for the this-pointer (essentially). This is why the second one works from within Private_derived or a friend of Private_derived.
First of all Derived should inherit from Base.
class Derived : public Base{
That said
First of you can just not have foo in Derived
class Base{
public:
void foo(){cout<<"base";}
};
class Derived : public Base{
}
int main(){
Derived bar;
bar.foo() // calls Base::foo()
return 0;
}
Second you can make Derived::foo call Base::foo.
class Base{
public:
void foo(){cout<<"base";}
};
class Derived : public Base{
public:
void foo(){ Base::foo(); }
^^^^^^^^^^
}
int main(){
Derived bar;
bar.foo() // calls Base::foo()
return 0;
}
Third you can use qualified id of Base::foo
int main(){
Derived bar;
bar.Base::foo(); // calls Base::foo()
return 0;
}
Consider making foo() virtual in the first place.
class Base {
public:
virtual ~Base() = default;
virtual void foo() { … }
};
class Derived : public Base {
public:
virtual void foo() override { … }
};
However, this does the job:
int main() {
Derived bar;
bar.Base::foo();
return 0;
}
An important [additional] note: you will still have compilation errors if Name Hiding occurs.
In this case, either utilize the using keyword, or use the qualifer. Additionally, see this answer as well.
#include <iostream>
class Base{
public:
void foo(bool bOne, bool bTwo){std::cout<<"base"<<bOne<<bTwo;}
};
class Derived : public Base
{
public:
void foo(bool bOne){std::cout<<"derived"<<bOne;}
};
int main()
{
Derived bar;
//bar.foo(true,true); // error: derived func attempted
bar.foo(true); // no error: derived func
bar.Base::foo(true,true); // no error: base func, qualified
return 0;
}