In C++, Is a Function Automatically Virtual If It Overrides a Virtual Function

In C++, is a function automatically virtual if it overrides a virtual function?

Standard 10.3.2 (class.virtual) says:

If a virtual member function vf is declared in a class Base and in a class Derived, derived directly or indirectly from Base, a member function vf with the same name and same parameter list as Base::vf is declared, then Derived::vf is also virtual (whether or not it is so declared) and it overrides*

[Footnote: A function with the same name but a different parameter list (clause over) as a virtual function is not necessarily virtual and does not override. The use of the virtual specifier in the declaration of an overriding function is legal but redundant (has empty semantics). Access control (clause class.access) is not considered in determining overriding. --- end foonote]

Overriding C++ pure virtual functions

Is the keyword "override" always necessary? If not, what are the best practices?

It is never "necessary". Overriding works with or without this keyword. It is only here to help you prevent issues like typos etc.

struct A
{
virtual int foo();
};

struct B: public A
{
int fooo(); //whoops, not overriding, no compiler error
};

struct C: public A
{
int fooo() override; //compiler error, compiler noticed my typo
};

So, the best practice is to always use override keyword when you want to override a virtual function.


The main question: I know the code above works for me. But I have the problem, that I basically have to "copy" the function signature of the pure virtual function out of the base class into my derived class. What happens, if I don't know what pure virtual functions the base class has?

You cannot not know that. To derive from class, compiler requires full definition of that class, which typically means you have #included it (and you have access to that definition).


My implementation above implies that I have to know all the pure virtual functions available in the base class. I tried accessing the pure virtual function by the Mode:: scope and LocalMode:: scope but in Visual Studio I simply got some error messages (I deem those error messages to be rather irrelevant to this question).

Are you looking for reflection mechanism? It's not present in C++, so you cannot e.g. get a list of function for given class. If you want to call pure virtual function from another function, that cannot work because, well, they are pure virtual.


Some plug-ins/Intellisense?

That is explicitly off-topic for StackOverflow, but there are many IDEs for C++, you shouldn't have any trouble finding them.

C++ virtual keyword for functions in derived classes. Is it necessary?

They are exactly the same. There is no difference between them other than that the first approach requires more typing and is potentially clearer.

Is an overridden pure virtual function, virtual?

Yes, both Square::getArea and FunnySquare::getArea are virtual too.

(emphasis mine)

Then this function in the class Derived is also virtual (whether or not the keyword virtual is used in its declaration) and overrides Base::vf (whether or not the word override is used in its declaration).

Why do we need virtual functions in C++?

Without "virtual" you get "early binding". Which implementation of the method is used gets decided at compile time based on the type of the pointer that you call through.

With "virtual" you get "late binding". Which implementation of the method is used gets decided at run time based on the type of the pointed-to object - what it was originally constructed as. This is not necessarily what you'd think based on the type of the pointer that points to that object.

class Base
{
public:
void Method1 () { std::cout << "Base::Method1" << std::endl; }
virtual void Method2 () { std::cout << "Base::Method2" << std::endl; }
};

class Derived : public Base
{
public:
void Method1 () { std::cout << "Derived::Method1" << std::endl; }
void Method2 () { std::cout << "Derived::Method2" << std::endl; }
};

Base* basePtr = new Derived ();
// Note - constructed as Derived, but pointer stored as Base*

basePtr->Method1 (); // Prints "Base::Method1"
basePtr->Method2 (); // Prints "Derived::Method2"

EDIT - see this question.

Also - this tutorial covers early and late binding in C++.

How to override a virtual function with a non-virtual function?

You are looking for a way to overrride a virtual function, so that it is no longer virtual.

Possible approaches using inheritance

Unfortunately, you cannot get rid of the virtuality of the member function once it is declared virtual. This is a direct consequence of the C++ Standard:

10.3/2: If a virtual member function vf is declared in a class Base and in a class Derived, derived directly or indirectly from Base,
a member function vf with the same name, parameter-type-list ,
cv-qualification, and refqualifier (or absence of same) as Base::vf is
declared, then Derived::vf is also virtual.

The use of final will not solve your problem: it will just forbid you to override the function in more derived classes. The function will remain virtual.

There is however an (unconvenient) trick to remove virtualisation at one specific level, using multiple inheritance:

class A {
public:
virtual void foo() { cout << "A" << endl; }
};
class B : public A {
public:
void foo() { cout << "B" << endl; }
};
class C : public B {
public:
void foo() { cout << "C" << endl; }
};
class EH { // Helper class, does not derive from A
public: // so foo() is non virtual here
void foo() { cout << "EH!" << endl; }
};
class E : public B, public EH { // inherits the virtual foo and the non virtual one
public:
using EH::foo; // We just say to use the non virtual one
};

The class E inherits from both the virtual and the non virtual. We just say to use the non virtual one if one calls it:

E e; 
e.foo(); // calls the non virtual function EH::foo(); => EH!
B* pb2 = &e;
pb2->foo(); // calls the original virtual function B::foo() => B

Be aware that this trick works only for the current level: If you'd derive a class form E, the class would also inherit indirectly from A, and here is the virtual curse again !

What do you intend to achieve ?

With virtual functions, you ensure that you always call the appropriate function corresponding to the real idendity of your object, regardless the fact that you use a pointer to a base. That's the goal of polymorphism.

With non-virtual function, your compiler invokes the function he thinks is the correct one, according to the type you are accessing to. If you access the object via a valid base pointer it will hence use the function of the base class instead of the derived one. Is this really what you want ?

if yes, just do this:

C c;
B* pb = &c;
pb->foo(); // uses the virtual function
pb->B::foo(); // but you can force to use the function, ignoring the virtuality.

Possible approach using a virtual and a non virtual function

With little additional cost you could emulate this behaviour in your code, using a comibnation of 2 functions: a private virtual one, and a public non virtual:

class A {
virtual void foo2() { cout << "A" << endl; } // virtual function
public:
void foo() { foo2(); } // non virtual function calling the virtual one
};
class B : public A {
void foo2() { cout << "B" << endl; } // overriding virtual
};
class C : public B {
public:
void foo() { cout << "C" << endl; } // ignore the virtual and override the non virtual function :-)
};

Can you override a pure virtual function within the same class?

I want to keep this interface in subclasses and be able to override it,

That will be already the case automatically, because you inherited it at the public access level.

for example I have a class for a Game, which cleans the screen, draw stuff and than flip the display buffer ...

...
Is there any way to do this sort of thing in C++11?

Completely independent of any c++11 particularities, just write an implementation for the abstract function declaration, and add an additional layer of indirection (aka the Template Method Pattern):

class Game : public IDraw {
public:
// Keep the interface
// This can be overridden by sub classes
void do_draw(Screen *scr) override {
OnPreDraw(scr);
OnDraw(scr);
OnPostDraw(scr);
}
protected:
virtual void OnPreDraw(Screen *scr) {
// Default implementation
scr->clear();
}
virtual void OnDraw(Screen *scr) = 0; // << Class is still abstract
virtual void OnPostDraw(Screen *scr) {
// Default implementation
scr->present();
}
};

This would allow to inject any implementation of Game at that finer grained sequence of operations, but keep default behavior from the base class implementation.

Also the base class is still abstract and effectively forces any derived class to implement OnDraw(), which is effectively the same as do_draw().

but since I need many class doing this kind of stuff it will end with plenty of names for the same concept.

No. As far your concept just involves the operations

 OnPreDraw(scr);
OnDraw(scr);
OnPostDraw(scr);

in that sequence, that won't change for the whole class inheritance hierarchy anymore in future.


To an extend:

You can also do that with Mixin pattern classes1

template<typename Derived>
class AbstractIDrawImpl : public IDraw {
void do_draw(Screen *scr) override {
static_cast<Derived*>(this)->OnPreDraw(scr);
static_cast<Derived*>(this)->OnDraw(scr);
static_cast<Derived*>(this)->OnPostDraw(scr);
}

// Expects public implementations
void OnPreDraw(Screen *scr) {
// Default implementation
scr->clear();
}
// Just no default implementation for
// void OnDraw(Screen *scr) << Class is still abstract
void OnPostDraw(Screen *scr) {
// Default implementation
scr->present();
}
};

The above mixin example can be bound to any implementation of IDraw that provides public functions for OnPreDraw() , OnDraw() and OnPostDraw():

class MyGame : public AbstractIDrawImpl<MyGame> {
public:
// IDraw interface implementation
void OnPreDraw(Screen *scr) {
// Call base class implementation
AbstractIDrawImpl<MyGame>::OnPreDraw(scr);
// E.g fill my background here
}
void OnDraw(Screen *scr) {
// For each game entity call
// IDraw::do_draw(scr);
for(auto drawableEntity : drawableEntities_) {
drawableEntity->do_draw(scr);
}
}
// Skip implementation of OnPostDraw()
private:
std::vector<std::shared_ptr<IDraw>> drawableEntities_;
};

1)

That pattern is well described with Alexei Andrescou's Policy based design paradigm and heavily used with Microsoft's ATL.



Related Topics



Leave a reply



Submit