I'm looking at some C++ example code, which effectively has the following:
class Foo : public mynamespace::Bar
{
public:
Foo()
{
// Do some stuff
}
void Delta() override
{
// Do some stuff
Bar::Delta();
}
};
I am having trouble understanding why the line Bar::Delta(); exists. Given that class Foo inherits class Bar, then surely when Foo::Delta() is called, this overrides anything existing in Bar::Delta(), and hence this line is redundant.
Or am I misunderstanding this whole inheritance thing? Maybe override doesn't override everything?
Bar::Delta();
is a function call. Isn't that what it looks like?
It's calling the base class version of Delta - by explicitly qualifying it as Bar::Delta - in addition to whatever extra stuff Foo's version does.
Maybe override doesn't override everything?
The override keyword just asks the compiler to verify you're really overriding a virtual function - otherwise, it's easy to accidentally write a new function which doesn't override anything (eg. because a parameter type is slightly different, or one version is const-qualified, or you changed the base class and forgot to update the derived class, or ...).
Here you are overriding the virtual function. That doesn't stop the base class implementation from existing, and as you've seen you can still call it.
You can (and should) test your intuition about this sort of thing yourself. Consider the trivial test code below. What do you think it will do?
Now actually run it. Were you right? If not, which part was unexpected?
#include <iostream>
using namespace std;
struct Bar {
virtual void Delta() {
cout << "Bar::Delta\n";
}
};
struct Foo : public Bar {
void Delta() override
{
cout << "Foo::Delta\n";
Bar::Delta();
}
};
int main()
{
cout << "b.Delta()\n";
Bar b;
b.Delta();
cout << "f.Delta()\n";
Foo f;
f.Delta();
cout << "pb->Delta()\n";
Bar *pb = &b;
pb->Delta();
cout << "pb->Delta()\n";
pb = &f;
pb->Delta();
}
This is a common pattern. In fact, the :: syntax for calling an overridden member function is there specifically for this situation.
It is very common for member function in a base class to perform some computation or action which can be done independently of the derived class, and let the derived class do things specific to the derivation.
Here is a fictitious example:
class Stock {
protected:
double totalDividend;
double baseDividend;
double adjustmentFactor;
public:
Stock(double d, double a)
: baseDividend(d), totalDividend(d), adjustmentFactor(a) {
}
virtual void double ComputeDividend() {
return totalDividend * adjustmentFactor;
}
};
class SpecialStock {
private:
double specialDividend;
public:
SpecialStock(double d, double sd, double a)
: Stock(d, a), specialDividend(sd) {
}
virtual void double ComputeDividend() override {
// Do some preparations
totalDividend = baseDividend + specialDividend;
// Call the overridden function from the base class
return Stock::ComputeDividend();
}
};
You seem to misunderstand what override means in c++. You should not really bother by it for your case. It's like a normal virtual function. override keyword is just a safety mechanism to ensure that a base class has matching function. It doesn't change anything other than semantic compile-time checks.
It is somewhat useful to guard against typical mismatches, such a const vs non-const versions, etc.
The virtual method mechanism does not replace the original member functions. It still is there in the Derived object. What happens is that a level of indirection is introduced, so a call to base.foo() uses a function pointer to call correct implementation which is Derived::Foo() in your case. But Base::Foo() still exists, and this is the syntax to "access" it. You can look up how exactly it work by searching materials on virtual methods.
Maybe override doesn't override everything?
The override specifier can be used to make compile-time checks when overriding a function that the function being overridden is virtual and is in fact being overridden.
why the line Bar::Delta(); exists
This line calls the base Delta function which might have some useful tasks to perform even though you have overridden it.
A simple example:
class Base
{
public:
virtual ~Base() {}
virtual void Foo()
{
// run tasks that are common to all derived types
}
};
class Derived : public Base
{
public:
void Foo() override
{
Base::Foo(); // we have to call this explicitly
// run tasks specific to the derived type
}
};
Delta in foo is a virtual method which "does some stuff" and then calls the base class's implementation of Delta.
override does not override anything, declaring the method as virtual does that. override is just for the compiler to throw syntax error in case the parent class doesn't have the Delta method.
Related
I did a simple test today:
struct C{virtual void f()=0;};
void C::f(){printf("weird\n");}
The program is OK, but is weird to me, when we use =0 it means the function body should be defined in the inherited classes, but it seems I can still give it implementation function.
I tried both GCC and VC, both OK. So it seems to me this should be part of C++ standard.
But why this is not a syntax error?
A reason I could think of is like C# having both 'interface' and 'abstract' keywords, interface can't have an implementation, while abstract could have some implementations.
Is this the case for my confusion, that C++ should support such a kind of weird syntax?
C++ Supports pure virtual functions with an implementation so class designers can force derived classes to override the function to add specific details , but still provide a useful default implementation that they can use as a common base.
Classic example:
class PersonBase
{
private:
string name;
public:
PersonBase(string nameIn) : name(nameIn) {}
virtual void printDetails() = 0
{
std::cout << "Person name " << name << endl;
}
};
class Student : public PersonBase
{
private:
int studentId;
public:
Student(string nameIn, int idIn) : PersonBase(nameIn), studentId(idIn) { }
virtual void printDetails()
{
PersonBase::printDetails(); // call base class function to prevent duplication
std::cout << "StudentID " << studentId << endl;
}
};
Others mentioned language consistency with the destructor, so I'll go for a software engineering stand-point:
It's because the class you are defining may have a valid default implementation, but calling it is risky/expansive/whatever. If you don't define it as pure virtual, derived classes will inherit that implementation implicitly. And may never know until run-time.
If you define it as pure virtual, a derived class must implement the function. And if it's okay with the risk/cost/whatever, it can call the default implementation statically as Base::f();
What's important is that it's a conscious decision, and the call is explicit.
Basically, the best of both worlds (or the worst...).
The derived class is required to implement the pure virtual method, the designer of the base class requires this for some reason. And the base class also provides a default implementation of this method that, if the derived class desires or requires it, can be used.
So some sample code could look like;
class Base {
public:
virtual int f() = 0;
};
int Base::f() {
return 42;
}
class Derived : public Base {
public:
int f() override {
return Base::f() * 2;
}
};
So what is a common use case...
A common use case for this technique is related to the destructor - basically the designer of the base class desires that it is an abstract class, but none of the methods make much sense as being pure virtual functions. The destructor is a feasible candidate.
class Base {
public:
~Base() = 0;
};
Base::~Base() { /* destruction... */ }
A pure virtual function must be overriden in subclasses. However, you can provide a default-implementation, that will work for sub-classes, but might not be optimal.
A constructed use case is for abstract shapes, e.g.
class Shape {
public:
virtual Shape() {}
virtual bool contains(int x, int y) const = 0;
virtual int width() const = 0;
virtual int height() const = 0;
virtual int area() const = 0;
}
int Shape::area() const {
int a = 0;
for (int x = 0; x < width(); ++x) {
for (int y = 0; y < height(); ++y) {
if (contains(x,y)) a++;
}
}
return a;
}
The area method will work for any shape, but is highly inefficient. Subclassers are encouraged to provide a suitable implementation, but if there is none available, they still can explicitely call the base class's method
Pure virtual means "child must override".
So:
struct A{ virtual void foo(){}; };
struct B:A{ virtual void foo()=0; };
struct C:B{ virtual void foo(){}; };
struct D:C{ virtual void foo()=0; };
void D::foo(){};
struct E:D{ virtual void foo(){D::foo();}; };
A has a virtual foo.
B makes it abstract. Before making an instance, derived types must implement it now.
C implements it.
D makes it abstract, and adds an imllementation.
E implements it by calling D's implementation.
A, C and E can have instances created. B and D cannot.
The technique of abstract with implementation can be used to provide a partial or inefficient implementation that derived types can call explicitly when they want to use it, but do not get "by default" because that would be ill advised.
Another intersting use case is where the parent interface is in flux, and tue code base is large. It has a fully functional implementation. Children who use the default must repeat the signature and forward explicitly to it. Those that want to override simply override.
When the base class sigrnature changes, the code will fail to compile unless every child either explicitly calls the default or properly overrides. Prior to the override keyword this was the only way to ensure you did not accidentally create a new virtual function instead of overriding a parent, and it remains the only way where the policy is enforced in the parent type.
Please note that you cannot instantiate an object with pure virtual methods.
Try to instantiate:
C c;
with VC2015, there is an error as expected:
1>f:\dev\src\consoleapplication1\consoleapplication1.cpp(12): error C2259: 'C': cannot instantiate abstract class
1>f:\dev\src\consoleapplication1\consoleapplication1.cpp(12): note: due to following members:
1>f:\dev\src\consoleapplication1\consoleapplication1.cpp(12): note: 'void C::f(void)': is abstract
1>f:\dev\src\consoleapplication1\consoleapplication1.cpp(6): note: see declaration of 'C::f'
To answer your question:
The mechanisms only declares the function to be pure virtual, but there is still the virtual function table and the baseclass. It will avoid you instanciate Baseclass (C), but does not avoid using it:
struct D : public C { virtual void f(); };
void D::f() { printf("Baseclass C::f(): "); C::f(); }
...
D d;
d.f();
The destructor must be defined, even if it is pure virtual. If you don't define the destructor the compiler will generate one.
Edit: you can't leave destructor declared without define, will cause link error.
You can anyway call the body of the function from derived classes.
You can implement the body of a pure virtual function to provide a default behavior, and at the same time you want that the designer of the derived class use that function explicitly.
I did a simple test today:
struct C{virtual void f()=0;};
void C::f(){printf("weird\n");}
The program is OK, but is weird to me, when we use =0 it means the function body should be defined in the inherited classes, but it seems I can still give it implementation function.
I tried both GCC and VC, both OK. So it seems to me this should be part of C++ standard.
But why this is not a syntax error?
A reason I could think of is like C# having both 'interface' and 'abstract' keywords, interface can't have an implementation, while abstract could have some implementations.
Is this the case for my confusion, that C++ should support such a kind of weird syntax?
C++ Supports pure virtual functions with an implementation so class designers can force derived classes to override the function to add specific details , but still provide a useful default implementation that they can use as a common base.
Classic example:
class PersonBase
{
private:
string name;
public:
PersonBase(string nameIn) : name(nameIn) {}
virtual void printDetails() = 0
{
std::cout << "Person name " << name << endl;
}
};
class Student : public PersonBase
{
private:
int studentId;
public:
Student(string nameIn, int idIn) : PersonBase(nameIn), studentId(idIn) { }
virtual void printDetails()
{
PersonBase::printDetails(); // call base class function to prevent duplication
std::cout << "StudentID " << studentId << endl;
}
};
Others mentioned language consistency with the destructor, so I'll go for a software engineering stand-point:
It's because the class you are defining may have a valid default implementation, but calling it is risky/expansive/whatever. If you don't define it as pure virtual, derived classes will inherit that implementation implicitly. And may never know until run-time.
If you define it as pure virtual, a derived class must implement the function. And if it's okay with the risk/cost/whatever, it can call the default implementation statically as Base::f();
What's important is that it's a conscious decision, and the call is explicit.
Basically, the best of both worlds (or the worst...).
The derived class is required to implement the pure virtual method, the designer of the base class requires this for some reason. And the base class also provides a default implementation of this method that, if the derived class desires or requires it, can be used.
So some sample code could look like;
class Base {
public:
virtual int f() = 0;
};
int Base::f() {
return 42;
}
class Derived : public Base {
public:
int f() override {
return Base::f() * 2;
}
};
So what is a common use case...
A common use case for this technique is related to the destructor - basically the designer of the base class desires that it is an abstract class, but none of the methods make much sense as being pure virtual functions. The destructor is a feasible candidate.
class Base {
public:
~Base() = 0;
};
Base::~Base() { /* destruction... */ }
A pure virtual function must be overriden in subclasses. However, you can provide a default-implementation, that will work for sub-classes, but might not be optimal.
A constructed use case is for abstract shapes, e.g.
class Shape {
public:
virtual Shape() {}
virtual bool contains(int x, int y) const = 0;
virtual int width() const = 0;
virtual int height() const = 0;
virtual int area() const = 0;
}
int Shape::area() const {
int a = 0;
for (int x = 0; x < width(); ++x) {
for (int y = 0; y < height(); ++y) {
if (contains(x,y)) a++;
}
}
return a;
}
The area method will work for any shape, but is highly inefficient. Subclassers are encouraged to provide a suitable implementation, but if there is none available, they still can explicitely call the base class's method
Pure virtual means "child must override".
So:
struct A{ virtual void foo(){}; };
struct B:A{ virtual void foo()=0; };
struct C:B{ virtual void foo(){}; };
struct D:C{ virtual void foo()=0; };
void D::foo(){};
struct E:D{ virtual void foo(){D::foo();}; };
A has a virtual foo.
B makes it abstract. Before making an instance, derived types must implement it now.
C implements it.
D makes it abstract, and adds an imllementation.
E implements it by calling D's implementation.
A, C and E can have instances created. B and D cannot.
The technique of abstract with implementation can be used to provide a partial or inefficient implementation that derived types can call explicitly when they want to use it, but do not get "by default" because that would be ill advised.
Another intersting use case is where the parent interface is in flux, and tue code base is large. It has a fully functional implementation. Children who use the default must repeat the signature and forward explicitly to it. Those that want to override simply override.
When the base class sigrnature changes, the code will fail to compile unless every child either explicitly calls the default or properly overrides. Prior to the override keyword this was the only way to ensure you did not accidentally create a new virtual function instead of overriding a parent, and it remains the only way where the policy is enforced in the parent type.
Please note that you cannot instantiate an object with pure virtual methods.
Try to instantiate:
C c;
with VC2015, there is an error as expected:
1>f:\dev\src\consoleapplication1\consoleapplication1.cpp(12): error C2259: 'C': cannot instantiate abstract class
1>f:\dev\src\consoleapplication1\consoleapplication1.cpp(12): note: due to following members:
1>f:\dev\src\consoleapplication1\consoleapplication1.cpp(12): note: 'void C::f(void)': is abstract
1>f:\dev\src\consoleapplication1\consoleapplication1.cpp(6): note: see declaration of 'C::f'
To answer your question:
The mechanisms only declares the function to be pure virtual, but there is still the virtual function table and the baseclass. It will avoid you instanciate Baseclass (C), but does not avoid using it:
struct D : public C { virtual void f(); };
void D::f() { printf("Baseclass C::f(): "); C::f(); }
...
D d;
d.f();
The destructor must be defined, even if it is pure virtual. If you don't define the destructor the compiler will generate one.
Edit: you can't leave destructor declared without define, will cause link error.
You can anyway call the body of the function from derived classes.
You can implement the body of a pure virtual function to provide a default behavior, and at the same time you want that the designer of the derived class use that function explicitly.
So I recently accidentally called some virtual functions from the constructor of a base class, i.e. Calling virtual functions inside constructors.
I realise that I should not do this because overrides of the virtual function will not be called, but how can I achieve some similar functionality? My use-case is that I want a particular function to be run whenever an object is constructed, and I don't want people who write derived classes to have to worry about what this is doing (because of course they could call this thing in their derived class constructor). But, the function that needs to be called in-turn happens to call a virtual function, which I want to allow the derived class the ability to override if they want.
But because a virtual function gets called, I can't just stick this function in the constructor of the base class and have it get run automatically that way. So I seem to be stuck.
Is there some other way to achieve what I want?
edit: I happen to be using the CRTP to access other methods in the derived class from the base class, can I perhaps use that instead of virtual functions in the constructor? Or is much the same issue present then? I guess perhaps it can work if the function being called is static?
edit2: Also just found this similar question: Call virtual method immediately after construction
If really needed, and you have access to the factory.
You may do something like:
template <typename Derived, typename ... Args>
std::unique_ptr<Derived> Make(Args&&... args)
{
auto derived = std::make_unique<Derived>(std::forward<Args>(args));
derived->init(); // virtual call
return derived;
}
There is no simple way to do this. One option would be to use so-called virtual constructor idiom, hide all constructors of the base class, and instead expose static 'create' - which will dynamically create an object, call your virtual override on it and return (smart)pointer.
This is ugly, and what is more important, constrains you to dynamically created objects, which is not the best thing.
However, the best solution is to use as little of OOP as possible. C++ strength (contrary to popular belief) is in it's non-OOP specific traits. Think about it - the only family of polymorphic classess inside standard library are streams, which everybody hate (because they are polymorphic!)
I want a particular function to be run whenever an object is constructed, [... it] in-turn happens to call a virtual function, which I want to allow the derived class the ability to override if they want.
This can be easily done if you're willing to live with two restrictions:
the constructors in the entire class hierarchy must be non-public, and thus
a factory template class must be used to construct the derived class.
Here, the "particular function" is Base::check, and the virtual function is Base::method.
First, we establish the base class. It has to fulfill only two requirements:
It must befriend MakeBase, its checker class. I assume that you want the Base::check method to be private and only usable by the factory. If it's public, you won't need MakeBase, of course.
The constructor must be protected.
https://github.com/KubaO/stackoverflown/tree/master/questions/imbue-constructor-35658459
#include <iostream>
#include <utility>
#include <type_traits>
using namespace std;
class Base {
friend class MakeBase;
void check() {
cout << "check()" << endl;
method();
}
protected:
Base() { cout << "Base()" << endl; }
public:
virtual ~Base() {}
virtual void method() {}
};
The templated CRTP factory derives from a base class that's friends with Base and thus has access to the private checker method; it also has access to the protected constructors in order to construct any of the derived classes.
class MakeBase {
protected:
static void check(Base * b) { b->check(); }
};
The factory class can issue a readable compile-time error message if you inadvertently use it on a class not derived from Base:
template <class C> class Make : public C, MakeBase {
public:
template <typename... Args> Make(Args&&... args) : C(std::forward<Args>(args)...) {
static_assert(std::is_base_of<Base, C>::value,
"Make requires a class derived from Base");
check(this);
}
};
The derived classes must have a protected constructor:
class Derived : public Base {
int a;
protected:
Derived(int a) : a(a) { cout << "Derived() " << endl; }
void method() override { cout << ">" << a << "<" << endl; }
};
int main()
{
Make<Derived> d(3);
}
Output:
Base()
Derived()
check()
>3<
If you take a look at how others solved this problem, you will notice that they simply transferred the responsibility of calling the initialization function to client. Take MFC’s CWnd, for instance: you have the constructor and you have Create, a virtual function that you must call to have a proper CWnd instantiation: “these are my rules: construct, then initialize; obey, or you’ll get in trouble”.
Yes, it is error prone, but it is better than the alternative: “It has been suggested that this rule is an implementation artifact. It is not so. In fact, it would be noticeably easier to implement the unsafe rule of calling virtual functions from constructors exactly as from other functions. However, that would imply that no virtual function could be written to rely on invariants established by base classes. That would be a terrible mess.” - Stroustrup. What he meant, I reckon, is that it would be easier to set the virtual table pointer to point to the VT of derived class instead of keep changing it to the VT of current class as your constructor call goes from base down.
I realise that I should not do this because overrides of the virtual function will not be called,...
Assuming that the call to a virtual function would work the way you want, you shouldn't do this because of the invariants.
class B // written by you
{
public:
B() { f(); }
virtual void f() {}
};
class D : public B // written by client
{
int* p;
public:
D() : p( new int ) {}
void f() override { *p = 10; } // relies on correct initialization of p
};
int main()
{
D d;
return 0;
}
What if it would be possible to call D::f from B via VT of D? You will use an uninitialized pointer, which will most likely result in a crash.
...but how can I achieve some similar functionality?
If you are willing to break the rules, I guess that it might be possible to get the address of desired virtual table and call the virtual function from constructor.
Seems you want this, or need more details.
class B
{
void templateMethod()
{
foo();
bar();
}
virtual void foo() = 0;
virtual void bar() = 0;
};
class D : public B
{
public:
D()
{
templateMethod();
}
virtual void foo()
{
cout << "D::foo()";
}
virtual void bar()
{
cout << "D::bar()";
}
};
What is the purpose of the final keyword in C++11 for functions? I understand it prevents function overriding by derived classes, but if this is the case, then isn't it enough to declare as non-virtual your final functions? Is there another thing I'm missing here?
What you are missing, as idljarn already mentioned in a comment is that if you are overriding a function from a base class, then you cannot possibly mark it as non-virtual:
struct base {
virtual void f();
};
struct derived : base {
void f() final; // virtual as it overrides base::f
};
struct mostderived : derived {
//void f(); // error: cannot override!
};
It is to prevent a class from being inherited. From Wikipedia:
C++11 also adds the ability to prevent inheriting from classes or simply preventing overriding methods in derived classes. This is done with the special identifier final. For example:
struct Base1 final { };
struct Derived1 : Base1 { }; // ill-formed because the class Base1
// has been marked final
It is also used to mark a virtual function so as to prevent it from being overridden in the derived classes:
struct Base2 {
virtual void f() final;
};
struct Derived2 : Base2 {
void f(); // ill-formed because the virtual function Base2::f has
// been marked final
};
Wikipedia further makes an interesting point:
Note that neither override nor final are language keywords. They are technically identifiers; they only gain special meaning when used in those specific contexts. In any other location, they can be valid identifiers.
That means, the following is allowed:
int const final = 0; // ok
int const override = 1; // ok
"final" also allows a compiler optimization to bypass the indirect call:
class IAbstract
{
public:
virtual void DoSomething() = 0;
};
class CDerived : public IAbstract
{
void DoSomething() final { m_x = 1 ; }
void Blah( void ) { DoSomething(); }
};
with "final", the compiler can call CDerived::DoSomething() directly from within Blah(), or even inline. Without it, it has to generate an indirect call inside of Blah() because Blah() could be called inside a derived class which has overridden DoSomething().
Nothing to add to the semantic aspects of "final".
But I'd like to add to chris green's comment that "final" might become a very important compiler optimization technique in the not so distant future. Not only in the simple case he mentioned, but also for more complex real-world class hierarchies which can be "closed" by "final", thus allowing compilers to generate more efficient dispatching code than with the usual vtable approach.
One key disadvantage of vtables is that for any such virtual object (assuming 64-bits on a typical Intel CPU) the pointer alone eats up 25% (8 of 64 bytes) of a cache line. In the kind of applications I enjoy to write, this hurts very badly. (And from my experience it is the #1 argument against C++ from a purist performance point of view, i.e. by C programmers.)
In applications which require extreme performance, which is not so unusual for C++, this might indeed become awesome, not requiring to workaround this problem manually in C style or weird Template juggling.
This technique is known as Devirtualization. A term worth remembering. :-)
There is a great recent speech by Andrei Alexandrescu which pretty well explains how you can workaround such situations today and how "final" might be part of solving similar cases "automatically" in the future (discussed with listeners):
http://channel9.msdn.com/Events/GoingNative/2013/Writing-Quick-Code-in-Cpp-Quickly
Final cannot be applied to non-virtual functions.
error: only virtual member functions can be marked 'final'
It wouldn't be very meaningful to be able to mark a non-virtual method as 'final'. Given
struct A { void foo(); };
struct B : public A { void foo(); };
A * a = new B;
a -> foo(); // this will call A :: foo anyway, regardless of whether there is a B::foo
a->foo() will always call A::foo.
But, if A::foo was virtual, then B::foo would override it. This might be undesirable, and hence it would make sense to make the virtual function final.
The question is though, why allow final on virtual functions. If you have a deep hierarchy:
struct A { virtual void foo(); };
struct B : public A { virtual void foo(); };
struct C : public B { virtual void foo() final; };
struct D : public C { /* cannot override foo */ };
Then the final puts a 'floor' on how much overriding can be done. Other classes can extend A and B and override their foo, but it a class extends C then it is not allowed.
So it probably doesn't make sense to make the 'top-level' foo final, but it might make sense lower down.
(I think though, there is room to extend the words final and override to non-virtual members. They would have a different meaning though.)
A use-case for the 'final' keyword that I am fond of is as follows:
// This pure abstract interface creates a way
// for unit test suites to stub-out Foo objects
class FooInterface
{
public:
virtual void DoSomething() = 0;
private:
virtual void DoSomethingImpl() = 0;
};
// Implement Non-Virtual Interface Pattern in FooBase using final
// (Alternatively implement the Template Pattern in FooBase using final)
class FooBase : public FooInterface
{
public:
virtual void DoSomething() final { DoFirst(); DoSomethingImpl(); DoLast(); }
private:
virtual void DoSomethingImpl() { /* left for derived classes to customize */ }
void DoFirst(); // no derived customization allowed here
void DoLast(); // no derived customization allowed here either
};
// Feel secure knowing that unit test suites can stub you out at the FooInterface level
// if necessary
// Feel doubly secure knowing that your children cannot violate your Template Pattern
// When DoSomething is called from a FooBase * you know without a doubt that
// DoFirst will execute before DoSomethingImpl, and DoLast will execute after.
class FooDerived : public FooBase
{
private:
virtual void DoSomethingImpl() {/* customize DoSomething at this location */}
};
final adds an explicit intent to not have your function overridden, and will cause a compiler error should this be violated:
struct A {
virtual int foo(); // #1
};
struct B : A {
int foo();
};
As the code stands, it compiles, and B::foo overrides A::foo. B::foo is also virtual, by the way. However, if we change #1 to virtual int foo() final, then this is a compiler error, and we are not allowed to override A::foo any further in derived classes.
Note that this does not allow us to "reopen" a new hierarchy, i.e. there's no way to make B::foo a new, unrelated function that can be independently at the head of a new virtual hierarchy. Once a function is final, it can never be declared again in any derived class.
The final keyword allows you to declare a virtual method, override it N times, and then mandate that 'this can no longer be overridden'. It would be useful in restricting use of your derived class, so that you can say "I know my super class lets you override this, but if you want to derive from me, you can't!".
struct Foo
{
virtual void DoStuff();
}
struct Bar : public Foo
{
void DoStuff() final;
}
struct Babar : public Bar
{
void DoStuff(); // error!
}
As other posters pointed out, it cannot be applied to non-virtual functions.
One purpose of the final keyword is to prevent accidental overriding of a method. In my example, DoStuff() may have been a helper function that the derived class simply needs to rename to get correct behavior. Without final, the error would not be discovered until testing.
Final keyword in C++ when added to a function, prevents it from being overridden by derived classes.
Also when added to a class prevents inheritance of any type.
Consider the following example which shows use of final specifier. This program fails in compilation.
#include <iostream>
using namespace std;
class Base
{
public:
virtual void myfun() final
{
cout << "myfun() in Base";
}
};
class Derived : public Base
{
void myfun()
{
cout << "myfun() in Derived\n";
}
};
int main()
{
Derived d;
Base &b = d;
b.myfun();
return 0;
}
Also:
#include <iostream>
class Base final
{
};
class Derived : public Base
{
};
int main()
{
Derived d;
return 0;
}
Final keyword have the following purposes in C++
If you make a virtual method in base class as final, it cannot be overridden in the derived class. It will show a compilation error:
class Base {
public:
virtual void display() final {
cout << "from base" << endl;
}
};
class Child : public Base {
public:
void display() {
cout << "from child" << endl;
}
};
int main() {
Base *b = new Child();
b->display();
cin.get();
return 0;
}
If we make a class as final, it cannot be inherited by its child classes:
class Base final {
public:
void displayBase() {
cout << "from base" << endl;
}
};
class Child :public Base {
public:
void displayChild() {
cout << "from child" << endl;
}
};
Note: the main difference with final keyword in Java is ,
a) final is not actually a keyword in C++.
you can have a variable named as final in C++
b) In Java, final keyword is always added before the class keyword.
Supplement to Mario Knezović 's answer:
class IA
{
public:
virtual int getNum() const = 0;
};
class BaseA : public IA
{
public:
inline virtual int getNum() const final {return ...};
};
class ImplA : public BaseA {...};
IA* pa = ...;
...
ImplA* impla = static_cast<ImplA*>(pa);
//the following line should cause compiler to use the inlined function BaseA::getNum(),
//instead of dynamic binding (via vtable or something).
//any class/subclass of BaseA will benefit from it
int n = impla->getNum();
The above code shows the theory, but not actually tested on real compilers. Much appreciated if anyone paste a disassembled output.
I have a class template where some methods are defined as virtual to give the ability for the user of my class to give an implementation for them in his derived class. Note that in my template class there is some non-virtual methods that makes use of the virtual one (a virtual class that should return a value is called in a non-virtual class).
Can you give me a simple example of a correct code where the virtual method of the parent class should return a value (but it's implementation is provided in a child class) and the value returned by the virtual method in the parent class is used in other methods of that class. Because I saw somewhere (for example here: Safely override C++ virtual functions) that this can cause some problems and the user defined method will note override the virtual method of the parent class.
Note: I program with Code::Blocks using g++ compiler.
EDIT: as requested here a simple example of what I want:
template<typename T>
class parent {
public:
// Public methods that user can call
int getSomething(T t);
void putSomething(T t, int x);
// public method that user should implement in his code
virtual float compute(T t) { }
// protected or private methods and attributes used internally by putSomething ...
float doComplexeThings(...); // this can call
};
The method compute() should be implemented by the user (the child class). However, this method compute() is called by putSomething() and doComplexeThings() for example.
If you can use C++11 features in your compiler then overrides can be tagged as so with the override special identifier:
float compute() override;
The above line in a derived class will cause a compiler error as the function does not override a member function in the base (incorrect signature, missing argument). But note that this must be done in each derived class, it is not a solution that you can impose from the base class.
From the base class you can only force the override by making the function pure virtual, but that changes the semantics. It does not avoid problems while overriding, but rather forces overriding in all cases. I would avoid this approach, and if you are to follow it and there is a sensible implementation for the base type, make the function virtual and provide a definition so that your derived classes's implementation can just call the functions the base type (i.e. you force the implementation, but in the simplest cases it will just forward the call to the parent)
You just have to make sure that the methods have the same signature (including const/mutable modifiers and argument types). You can use a pure virtual definition to provoke compiler errors if you fail to override the function in a subclass.
class parent {
public:
// pure virtual method must be provided in subclass
virtual void handle_event(int something) = 0;
};
class child : public parent {
public:
virtual void handle_event(int something) {
// new exciting code
}
};
class incomplete_child : public parent {
public:
virtual void handle_event(int something) const {
// does not override the pure virtual method
}
};
int main() {
parent *p = new child();
p->handle_event(1); // will call child::handle_event
parent *p = new incomplete_child(); // will not compile because handle_event
// was not correctly overridden
}
This question is asked in 2013. It's pretty old but I found something new which doesn't exist in the answers.
We need to understanding three concept is overload, overwrite, and hide.
Short answer, you want to overload the inheritance function from base class.
However, overload is the mechanism to add multiple behavior for function which needs all these functions under the same scale. But the virtual function is in the Base class obviously.
class A {
public:
virtual void print() {
cout << id_ << std::endl;
}
private:
string id_ = "A";
};
class B : A {
public:
using A::print;
void print(string id) {
std::cout << id << std::endl;
}
};
int main(int argc, char const *argv[]) {
/* code */
A a;
a.print();
B b;
b.print();
b.print("B");
return 0;
}
Add using A::print; in your derive class will do the work!
Though I don't feel it's a good idea since the philosophy behind the overload and inheritance is different, it may not a good idea to nest them together.