Administrivia
One suggestion
Fast to follow
No need to poll
Some are still boring, some are having troubles
Can we slow down?
Future Schedules
We have final presentation
I am preparing extra lectures for technical programming tips
Surprise: Your have learned basic grammar of C++ already
Next lectures on
STL, Memory management
Searching, sorting, Recursion
Library, Makefile
1
Administrivia
Please
Surprise: Your have learned basic grammar of C++ already
Read book chapters every time after class
Practice the concepts while you are doing TP
Start your TP ASAP
But I will review every time to help you
Bring your in-class questions for you and your friends, PLEASE
Extra points are still in action. Email me for points.
Once I notice your question point, I will prepare extra ppts for your
understanding
ANYTIME, Use Piazza or Email me or TAs
I am trying to answer back ASAP within few hours
For assignment inputs, email TAs
2
Polymorphism and Virtual
Functions
Chapter 15
Instructor: Sungahn Ko
2016 Spring CSE24101
Example
class AAA {
public:
AAA
(virtual) void fct() {
cout << “AAA"; }};
class BBB: public AAA {
public: BBB
void fct() {
cout << “BBB”
Result?
int main() { w/ or w/o virtual?
BBB b;
b.fct();
}
Output: BBB
Always.
This is static binding
4
Example
class AAA {
public:
AAA
(virtual) void fct() {
cout << “AAA"; }};
class BBB: public AAA {
public: BBB
void fct() {
cout << “BBB”
int main() {
BBB * b = new BBB; w/o virtual output:
b-> fct();
AAA* a = b; BBB
A->fct();
AAA
}
w/ virtual output
BBB BBB
5
Example
class Car {
public:
Car
virtual void Create() {
cout << " Car\n"; }};
class Sedan: public Car {
public: Sedan
void Create() {
cout << " Sedan }};
int main() {
w/o virtual: Car, Car
Car *x, *y; w/ virtual: Car, Sedan
x = new Car();
x->Create();
y = new Sedan();
A question from a student?
y->Create();
} w/ virtual at Sedan Create:
Car, Car
6
VTABLE
7
15.1 Type Compatibility in
Inheritance Hierarchies
Classes lower in the
hierarchy are special general Animal
case
cases of those above
-Sometimes, we may want to Cat Dog
instantiate all of these for
purposes
-But based on situations, I
want my instances act
differently. special
- How to easily do this? case Poodle
Polymorphism in OOP
8
Q&A
9
Type Compatibility in Inheritance
A pointer to a derived class can be assigned to a
pointer to a base class. Another way to say this is:
A base class pointer can point to derived class
objects
Animal *pA = new Cat;
10
Type Compatibility in Inheritance
Assigning a base class pointer to a derived class
pointer requires a cast
Animal *pA = new Cat;
Cat *pC;
pC = static_cast<Cat *>(pA);
The base class pointer must already point to a
derived class object for this to work
11
Using Type Casts with Base Class
Pointers
C++ uses the declared type of a pointer to determine
access to the members of the pointed-to object
If an object of a derived class is pointed to by a base
class pointer, all members of the derived class may not be
accessible
Type cast the base class pointer to the derived class (via
static_cast) in order to access members that are
specific to the derived class
12
Example
enum Discipline { ARCHEOLOGY, BIOLOGY, class Faculty:public Person
COMPUTER_SCIENCE }; {
class Person private:
{ Discipline department;
protected: public:
string name; //constructor
public: Faculty(string fname, Discipline d) :
Person() { setName(""); } Person(fname)
Person(string pName) { setName(pName); } {
void setName(string pName) department = d;
{ name = pName; } }
string getName() { return name;} void setDepartment(Discipline d)
}; { department = d; }
Discipline getDepartment( )
{ return department; }
};
13
Example
class TFaculty : public Faculty
{
private:
string title; Person
public:
TFaculty(string fname, Discipline d, string title)
: Faculty(fname, d) { setTitle(title); }
void setTitle(string title) { this->title = title; }
//override getName() Faculty
string getName( )
{ return title + " " + Person::getName();}
};
TFaculty
14
Using Type Casts with Base Class
Pointers
// pPerson actually points to Faculty object
// but not aware of additional members of
// Faculty class
Person *pPerson = new Faculty(“Donald Knuth”,
COMPUTER_SCIENCE);
pPerson->setDepartment(BIOLOGY); // compile error!
static_cast<Faculty*>(pPerson)->setDepartment(BIOLOGY);
// work!
15
Example
int main() cout << static_cast<TFaculty *>(pp)->getName()
{ Person *pp; << endl;
Faculty *pf;
TFaculty *ptf; // Assigment from base to derived needs a cast.
ptf = new TFaculty("Indiana Jones", TFaculty *ptf1;
ARCHEOLOGY, "Dr."); ptf1 = static_cast<TFaculty *>(pp);
cout << "Get name through a pointer to cout << "Get name through a pointer to TFaculty: ";
TFaculty: "; cout << ptf1->getName();
cout << ptf->getName() << endl; return 0;
}
pf = ptf;
cout << "Get name through a pointer to Get name through a pointer to TFaculty: Dr. Indiana
Faculty: "; Jones
cout << pf->getName() << endl; Get name through a pointer to Faculty: Indiana Jones
Get name through a cast to pointer to TFaculty: Dr.
pp = ptf; Indiana Jones
cout << "Get name through a cast to pointer Get name through a pointer to TFaculty: Dr. Indiana
to TFaculty: "; Jones
16
15.2 Polymorphism and Virtual
Member Functions
Polymorphic code: Code that behaves differently when
it acts on objects of different types
Virtual Member Function: The C++ mechanism for
achieving polymorphism
17
Polymorphism
Consider the Animal,
Cat, Dog hierarchy
where each class has Animal
its own version of the
member function
id( ) Cat Dog
Poodle
18
Polymorphism
class Animal{
public: void id(){cout << "animal";}
}
class Cat : public Animal{
public: void id(){cout << "cat";}
}
class Dog : public Animal{
public: void id(){cout << "dog";}
}
19
Polymorphism
Consider the collection of different Animal objects
Animal *pA[] = {new Animal,
new Dog,
new Cat};
for(int k=0; k<3; k++)
pA[k]->id();
Q: What will be printed out?
A: Prints animal animal animal, ignoring the more specific versions
of id() in Dog and Cat
20
Polymorphism
Preceding code is not polymorphic: it behaves the same
way even though Animal, Dog and Cat have different
types and different id() member functions
Polymorphic code would have printed "animal dog
cat" instead of "animal animal animal"
21
Polymorphism
The code is not polymorphic because in the expression
pA[k]->id()
the compiler sees only the type of the pointer pA[k],
which is pointer to Animal
Compiler does not see type of actual object pointed to,
which may be Animal, or Dog, or Cat
22
Virtual Functions
Declaring a function virtual will make the compiler
check the type of each object in run-time to see if it is
a more specific version of the object.
23
Virtual Functions
class Animal{
public: virtual void id(){cout << "animal";}
}
class Cat : public Animal{
public: virtual void id(){cout << "cat";}
}
class Dog : public Animal{
public: virtual void id(){cout << "dog";}
}
----------------
class Animal{
public: void id(){cout << "animal";}
}
class Dog : public Animal{
One question from
public: virtual void id(){cout << “Dog";}
last class
}
Virtual in Dog
class Poodle : public Dog{
Result?
public: void id(){cout << “Poodle";}
}
24
Virtual Functions
No virtual
1. Virtual for id() in Animal
Animal dog poodle
2. no virtual for id() in Animal
Animial animial animial
3. Virtual for id2()
Dog2 poodle2
Compared to case 1, 3 above
4. Virtual for id() in Dog
Check it out!!!!
I will post this code at BB
Play with this for your
25 understanding
Static binding & virtual
w/o virtual:
Car
Car
w/ virtual in Car:
Car
Sedan
I will post this code at
BB
Play with virtual for
your understanding
26
Virtual Functions
If the member functions id()are declared virtual, then
the code
Animal *pA[] = {new Animal,
new Dog,
new Cat};
for(int k=0; k<3; k++)
pA[k]->id();
will print animal dog cat
27
Function Binding
In pA[k]->id(), compiler must choose which
version of id() to use: There are different versions in
the Animal, Dog, and Cat classes
Function binding is the process of determining which
function definition to use for a particular function call
The alternatives are static and dynamic binding
28
Static Binding
Static binding chooses the function in the class of the
base class pointer, ignoring any versions in the class of
the object actually pointed to
Static binding is done at compile time
29
Dynamic Binding
Dynamic Binding determines the function to be invoked at
execution time
Can look at the actual class of the object pointed to and
choose the most specific version of the function
Dynamic binding is used to bind virtual functions
30
15.3 Abstract Base Classes and Pure
Virtual Functions
An abstract class is a class that must be instantiated as
one of its subclasses (derived classes)
For example, in real life, Animal is an abstract class: there
are no animals that are not dogs, or cats, or lions…
31
Abstract Base Classes and Pure
Virtual Functions
Abstract classes are an organizational tool: useful in
organizing inheritance hierarchies
Abstract classes can be used to specify an interface that
must be implemented by all subclasses
32
Abstract Functions
The member functions specified in an abstract class do
not have to be implemented
The implementation is left to the subclasses
In C++, an abstract class is a class with at least one
abstract member function
33
Abstract Functions
(Pure Virtual Functions)
In C++, a member function of a class is declared to be an
abstract function by making it virtual and replacing its body
with = 0;
class Animal{
public:
virtual void id()=0;
};
A virtual function with its body omitted and replaced with =0
is called a pure virtual function, or an abstract function
34
Abstract Classes
An abstract class can not be instantiated
An abstract class can only be inherited from: that is, you
can derive classes from it
Classes derived from abstract classes must override the
abstract (pure virtual) function with a concrete member
function before they can be instantiated.
Note : The member functions in an abstract class do not have to
be implemented by sub-classes.
35
Abstract Classes
class Shape class Rectangle : public Shape
{ {
protected: public:
int posX, posY; virtual void draw(){
public: cout << “Rectangle at "
virtual void draw() = 0; << posX << " “ << posY
void setPosition(int pX,int pY) << endl;}
{ };
posX = pX;
posY = pY; class Hexagon : public Shape
} {
}; public:
virtual void draw(){
cout << “Hexagon at "
<< posX << " “ << posY
<< endl;}
};
36
Abstract Classes
int main() {
// Create array of pointers to Shapes of various types.
const int NUM_SHAPES = 3;
Shape * shapeArray[] = { new Hexagon, new Rectangle,
new Hexagon};
// Set positions of all the shapes.
int posX = 5, posY = 15;
for (int k = 0; k < NUM_SHAPES; k++) {
shapeArray[k]->setPosition(posX, posY);
posX += 10;
posY += 10; };
// Draw all the shapes at their positions.
for (int j = 0; j < NUM_SHAPES; j++)
shapeArray[j]->draw();
return 0; }
Hexagon at 5 15
Rectangle at 15 25
Hexagon at 25 35
37
Q&A
38
Virtual Goes Downward
class Animal{
public: virtual void id(){cout << "animal";}
}
class Cat : public Animal{
public: virtual void id(){cout << "cat";}
}
class Dog : public Animal{
public: virtual void id(){cout << "dog";}
}
----------------
class Animal{
public: void id(){cout << "animal";}
}
class Dog : public Animal{
public: virtual void id(){cout << “Dog";}}
class Poodle : public Dog{
public: void id(){cout << “Poodle";}}//don’t need to add virtual
Overriding only works from Dog, does not work for Animal’s
id() 39
VTABLE
40
Virtual -> DOWNWARD
class base {
public:
void fun() { cout<<"base"; }
};
class derived : public base {
public:
virtual void fun() {cout<<" derived";}
};
main() {
base *p;
derived d;
p=&d;
p->fun();
return 0;
}
Output : base
41