Polymorphism It simply means one name multiple forms

  • Slides: 12
Download presentation
Polymorphism • It simply means ‘one name, multiple forms’. • We have already seen

Polymorphism • It simply means ‘one name, multiple forms’. • We have already seen how the concepts of polymorphism implemented using overloaded function. • The overloaded member function are selected for invoking by matching arguments. • This information is known to the compiler at compile time and it is known as early binding. Also known as compile time polymorphism. 1

#include <iostream. h> class A { public : float sum() { return 10; }

#include <iostream. h> class A { public : float sum() { return 10; } float sum(float i, float j, float k) { return i+j+k; } }; class B : public A { public: using A: : sum; float sum(float i) { return i; } float sum(float i, int j) return i+j; } }; void main() { B calculate; cout<<calculate. sum(25. 5)<<endl; cout<<calculate. sum(4. 5, 3. 5, 2. 5)<<endl; cout<<calculate. sum()<<endl; } Output 25. 5 9. 5 10 {

 • Consider the situation where the function name and prototype is same in

• Consider the situation where the function name and prototype is same in both the base and derived classes. class A { int x; public: void show(){…. . } }; class B : public A { public: void show(){…. . } }; • Since the prototype is same, function is not overloaded. • Virtual function and pointer are used to invoke appropriate member function while the program is running and it is known as late binding. • Also known as runtime polymorphism. 3

// pointers to base class #include <iostream. h> int main () { CRectangle rect;

// pointers to base class #include <iostream. h> int main () { CRectangle rect; CTriangle trgl; class CPolygon { protected: int width, height; public: void set_values (int a, int b) { width=a; height=b; } }; CPolygon * p 1 = &rect; CPolygon * p 2 = &trgl; class CRectangle : public CPolygon { public: int area (void){ return (width * height); } }; class CTriangle: public CPolygon { public: int area (void){ return (width * height / 2); } }; p 1 ->set_values (4, 5); p 2 ->set_values (4, 5); cout << rect. area() << endl; cout << trgl. area() << endl; return 0; } 20 10 ﻭﺍﺋﻞ ﻗﺼﺎﺹ Code 4

 • The function main creates two pointers that point to objects of class

• The function main creates two pointers that point to objects of class CPolygon, that are *p 1 and *p 2. These are assigned to the addresses of rect and trgl, and because they are objects of classes derived from CPolygon they are valid assignations. • The only limitation of using *p 1 and *p 2 instead of rect and trgl is that both *p 1 and *p 2 are of type CPolygon* and therefore we can only refer to the members that CRectangle and CTriangle inherit from CPolygon. For that reason when calling the area() members we have not been able to use the pointers *p 1 and *p 2. • To make it possible for the pointers to class CPolygon to admit area () as a valid member, this should also have been declared in the base class and not only in its derived ones.

Virtual members • In order to declare an element of a class which we

Virtual members • In order to declare an element of a class which we are going to redefine in derived classes we must precede it with the keyword virtual so that the use of pointers to objects of that class can be suitable. 6

#include <iostream. h> class CPolygon { protected: int width, height; public: void set_values (int

#include <iostream. h> class CPolygon { protected: int width, height; public: void set_values (int a, int b) { width=a; height=b; } virtual int area (void) { return (0); } }; class CRectangle: public CPolygon { public: int area (void){ return (width * height); } }; class CTriangle: public CPolygon { public: int area (void) { return (width * height / 2); } }; ﻭﺍﺋﻞ ﻗﺼﺎﺹ int main () { CRectangle rect; CTriangle trgl; CPolygon poly; CPolygon * p 1 = &rect; CPolygon *p 2=&trgl; CPolygon * p 3 = &poly; p 1 ->set_values(4, 5); p 2 ->set_values(4, 5); p 3 ->set_values (4, 5); cout << p 1 ->area() << endl; cout << p 2 ->area() << endl; cout << p 3 ->area() << endl; } 20 10 0 7

 • The three classes (CPolygon, CRectangle and CTriangle) have the same members: width,

• The three classes (CPolygon, CRectangle and CTriangle) have the same members: width, height, set_values() and area(). • area() has been defined as virtual because it is later redefined in derived classes. You can verify if you want that if you remove this word (virtual) from the code and then you execute the program the result will be 0 for the three polygons instead of 20, 10, 0. That is because instead of calling the corresponding area() function for each object (CRectangle: : area(), CTriangle: : area() and CPolygon: : area(), respectively), CPolygon: : area() will be called for all of them since the calls are via a pointer to CPolygon. • Therefore, what the word virtual does is to allow a member of a derived class with the same name as one in the base class be suitably called when a pointer to it is used

Abstract base classes • Abstract classes are similar to the class CPolygon of our

Abstract base classes • Abstract classes are similar to the class CPolygon of our previous example. The only difference is that in our previous example we have defined a valid area() function for objects that were of class CPolygon (like object poly), whereas in an abstract base class we could have simply left without defining this function by appending = 0 to the function declaration. • The class CPolygon could have been thus: // abstract class CPolygon { protected: int width, height; }; public: void set_values(int a, int b){ width=a; height=b; } virtual int area (void) = 0;

 • This type of function is called a pure virtual function, and all

• This type of function is called a pure virtual function, and all classes that contain a pure virtual function (do-nothing function) are considered abstract base classes. • The greatest difference of an abstract base class is that instances (objects) of it cannot be created, but we can create pointers to them. Therefore a declaration likes: CPolygon poly; // incorrect CPolygon * ppoly 1; //correct • This is because the pure virtual function that it includes is not defined and it is impossible to create an object if it does not have all its members defined. A pointer that points to an object of a derived class where this function has been defined is perfectly valid. • The main objective of an abstract base class is to provide some traits to the derived classes and to create a base pointer required for achieving run time polymorphism.

#include <iostream. h> class CPolygon { protected: int width, height; public: void set_values (int

#include <iostream. h> class CPolygon { protected: int width, height; public: void set_values (int a, int b) { width=a; height=b; } virtual int area (void) = 0; }; class CRectangle: public CPolygon { public: int area (void) {return (width * height); } }; class CTriangle: public CPolygon { public: int area (void) {return (width * height / 2); } }; int main () { CRectangle rect; CTriangle trgl; CPolygon * ppoly 1 = &rect; CPolygon * ppoly 2 = &trgl; ppoly 1 ->set_values (4, 5); ppoly 2 ->set_values (4, 5); cout << ppoly 1 ->area() << endl; cout << ppoly 2 ->area() << endl; return 0; } 20 10

#include <iostream. h> int main () { Rectangle rect; Triangle trgl; Polygon * p

#include <iostream. h> int main () { Rectangle rect; Triangle trgl; Polygon * p 1 = &rect; Polygon * p 2 = &trgl; class Polygon { protected: int width, height; public: void set_values (int a, int b) { width=a; height=b; } p 1 ->set_values (4, 5); p 2 ->set_values (4, 5); p 1 ->printarea(); p 2 ->printarea(); virtual int area (void) =0; }; void printarea (void) { cout << area() << endl; } return 0; } class Rectangle: public Polygon { public: int area (void) { return (width * height); } }; 20 10 class Triangle: public Polygon { public: int area (void) { return (width * height / 2); } }; ﻭﺍﺋﻞ ﻗﺼﺎﺹ 12