Yes, it also helps when you want to modify the definition and if you just want to scan the definition, as well. Separating the two almost always results in advantages.
Virtual functions allow the compiler at run-time to what type of object it is that you're calling a function on. By doing this, it is possible to derive several classes from a common base class, and then call a virtual function inside the base class, and the compiler will actually call the same virtual function in the correct derived class:
Consequently, the destructor is no different. The destructor is called when invoking delete on a pointer, so the correct destructor will be called (imagine renaming class member function foo to the destructor and changing the function foo to take a pointer (allocated with new) and calling delete inside).Code:class CBase { public: virtual void foo() { cout << "Base\n"; } }; class CDerived1: public CBase { public: virtual void foo() { cout << "Derived1\n"; } }; class CDerived2: public CBase { public: virtual void foo() { cout << "Derived2\n"; } }; void foo(CBase& r) { r.foo(); } int main() { CBase b; CDerived1 d1; CDerived2 d2; foo(b); // Prints "Base" foo(d1); // Prints "Derived1" foo(d2); // Prints "Derived2" }
Fair enough. It's recommended you have a virtual destructor for classes that contains virtual functions.And I can't get rid of the virtual destructor because we get marked down for warnings
Read this FAQ on When should my destructor be virtual?What's the downside to leaving it like it is?
Look up a C++ Reference and learn How To Ask Questions The Smart WayOriginally Posted by Bjarne Stroustrup (2000-10-14)
Careful. "base class" and "parent class" are synonyms. The opposite is "derived" or "child class".Nothing in the base classes.
All the buzzt!
CornedBee
"There is not now, nor has there ever been, nor will there ever be, any programming language in which it is the least bit difficult to write bad code."
- Flon's Law
I think this is rather dangerous advice to give to someone who admits to "not ~really~" understanding virtual functions.
If Base doesn't have a virtual destructor, then ~Base gets called but ~Derived doesn't. Even if your ~Base doesn't do anything useful, someone else deriving from your Base might have a ~Derived which does, expecting it to be called.Code:Base *p = new Derived(); delete p;
Compilers generate this warning because if your class has virtual functions, it is apparently intended to be derived from.
--
Computer Programming: An Introduction for the Scientifically Inclined
In practice, yes, though by the rules of the C++ Standard it just results in undefined behaviour.If Base doesn't have a virtual destructor, then ~Base gets called but ~Derived doesn't.
Look up a C++ Reference and learn How To Ask Questions The Smart WayOriginally Posted by Bjarne Stroustrup (2000-10-14)
And with multiple inheritance, it might well crash if you don't give it a virtual destructor:
Crashes on GCC:Code:struct B1 { int d1, d2, d3; ~B1() {} }; struct B2 { int e1, e2, e3; ~B2() {} }; struct D : B1, B2 { int f1, f2, f3; }; int main() { B2 *b2 = new D; delete b2; }
*** glibc detected *** ./multip: free(): invalid pointer: 0x000000000060201c ***
The reason is that in GCC's internal model, the destructor returns a pointer to the actual start of the object, and that is passed to operator delete. If the destructor is not virtual, then you get the pointer to the B2 subobject, which is not the start of the object, and thus an address free() can't handle.
All the buzzt!
CornedBee
"There is not now, nor has there ever been, nor will there ever be, any programming language in which it is the least bit difficult to write bad code."
- Flon's Law