Continuing with Chapter 10
- Read this, and read it again.
- Daniel's Question
- class Derived: access_modifier Base
- See page 331
- Public: All public members of the base class are public in the derived class.
- Protected: All public members of the base class are protected members of the derived class
- Private, the default: All public members of the base class are private members of the derived class.
- The second two are not a "is-a" relationship.
- They are a way to reuse code
- Gregorie says "There are a handful of reason why you might want to degrade access ... but most reasons imply flaws in the design".
- Meyers says
- "Private inheritance means is-implemented-in-terms-of" relationship.
- He says use this sparingly.
- He says "I can't wrap my head around the meaning of protected inheritance".
- There are subtle issues here, just use public until you have a need to do better.
- Virtual functions
- The virtual keyword allows us to Override functions from the base class, not just hide them.
- This is only an issue when dealing with a pointer or reference.
- As we saw last time
- you can have a base class pointer to a derived class element.
- This is the basis for polymorphism.
- But how does it know what functions to call?
- Stroustrup has an interesting discussion.
- If we have a pointer and know it's type, no problem.
- We could keep a member indicating the type of object.
- But this would be messy as the number of objects grow.
- And most likely prone to error.
- We could do a cast by hand, but this can cause real errors
- Or we can have the compiler/run time system decide what to do.
- Creating virtual functions allows the last option to occur.
- So what happens
- For non virtual methods, they are bound at compile time.
- IE the compiler knows that type of each object and knows the address of the member function to call.
- It just puts that code in place.
- This is called static binding or early binding
- For virtual members this is not the case.
- If a class has a virtual member
- There is a table of function pointers.
- At run time, the table is consulted and the proper function is called.
- This is really Stroustrup's second scenario (and the last) but implemented by the compiler.
- This is called dynamic binding or late binding
- Apparently many languages like java make everything virtual.
- But this slows down function calls.
- And thus slows down your program.
- Gergorie says to make everything virtual
- Including destructors.
- But not constructors.
- Meyers is not quite so enthusiastic.
- Virtual Destructors
- If the base class destructor is not virtual any derived class destructors will "hide" but not override the base class destructor.
- So if you have a base class pointer to a derived class, the derived class destructor will not be called.
- override keyword
- function def override;
- Added in c++11
- This specifies that the given function overrides a virtual function.
- This is not required.
- But it will generate compiler errors if
- The base class function is not virtual.
- The base class and the declared function signatures do not match.
- We will see some alternatives here later.
- For now, Gregorie says you should use it.
- final keyword.
- Also c++11
- Applied to classes or member function.
- Stops further overriding of the member of class.
- Same as override in functions
- class classid final ... { in classes
- See override.cpp