0% found this document useful (0 votes)
22 views

Poly Unit 3

The document discusses different types of polymorphism in C++ including compile-time polymorphism and run-time polymorphism. Compile-time polymorphism includes function overloading and operator overloading, and is resolved at compile-time through static binding. Run-time polymorphism includes method overriding and is resolved at run-time through dynamic binding using virtual functions. The document also discusses concepts like type casting, mutable keyword, function overloading, and function overriding.

Uploaded by

Sahil Gupta
Copyright
© © All Rights Reserved
Available Formats
Download as DOCX, PDF, TXT or read online on Scribd
0% found this document useful (0 votes)
22 views

Poly Unit 3

The document discusses different types of polymorphism in C++ including compile-time polymorphism and run-time polymorphism. Compile-time polymorphism includes function overloading and operator overloading, and is resolved at compile-time through static binding. Run-time polymorphism includes method overriding and is resolved at run-time through dynamic binding using virtual functions. The document also discusses concepts like type casting, mutable keyword, function overloading, and function overriding.

Uploaded by

Sahil Gupta
Copyright
© © All Rights Reserved
Available Formats
Download as DOCX, PDF, TXT or read online on Scribd
You are on page 1/ 12

Polymorphism

The term "Polymorphism" is the combination of "poly" + "morphs" which means many
forms. It is a greek word.

Type of Polymorphism

Compile time polymorphism: The overloaded functions are invoked by matching the type
and number of arguments. This information is available at the compile time and, therefore,
compiler selects the appropriate function at the compile time. It is achieved by function
overloading and operator overloading which is also known as static binding or early binding.
Now, let's consider the case where function name and prototype is same.

Run time polymorphism: Run time polymorphism is achieved when the object's method is
invoked at the run time instead of compile time. It is achieved by method overriding which is
also known as dynamic binding or late binding.

Differences b/w compiles time and run time polymorphism.

Compile time polymorphism Run time polymorphism

The function to be invoked is known at the compile The function to be invoked is known at the run
time. time.

It is also known as overloading, early binding and It is also known as overriding, Dynamic
static binding. binding and late binding.

Overloading is a compile time polymorphism where Overriding is a run time polymorphism where
more than one method is having the same name but more than one method is having the same
with the different number of parameters or the type name, number of parameters and the type of
of the parameters. the parameters.

It is achieved by function overloading and operator It is achieved by virtual functions and pointers.
overloading.

It provides fast execution as it is known at the It provides slow execution as it is known at the
compile time. run time.

It is less flexible as mainly all the things execute at It is more flexible as all the things execute at
the compile time. the run time.

Concept of overloading
Creating two or more members that have the same name but are different in number or type
of parameter is known as overloading.

1) Function overloading
2) Operator overloading

Operator Overloading

Operator overloading is a compile-time polymorphism in which the operator is overloaded to


provide special meaning to the user-defined data type. Operator overloading is used to
overload or redefine most of the operators available in C++. It is used to perform the
operation on the user-defined data type.

return_type class_name : : operator op(argument_list)

// body of the function.

Rules for Operator Overloading

1) Existing operators can only be overloaded, but the new operators cannot be
overloaded.
2) The overloaded operator contains at least one operand of the user-defined data type.
3) We cannot use friend function to overload certain operators. However, the member
function can be used to overload those operators.
4) When unary operators are overloaded through a member function take no explicit
arguments, but, if they are overloaded by a friend function, takes one argument.
5) When binary operators are overloaded through a member function takes one explicit
argument, and if they are overloaded through a friend function takes two explicit
arguments.

Unary operator

The unary operators operate on a single operand and following are the examples of Unary
operators

The increment (++) and decrement (--) operators.

The unary minus (-) operator.

The logical not (!) operator.

The unary operators operate on the object for which they were called and normally, this
operator appears on the left side of the object, as in !obj, -obj, and ++obj but sometime they
can be used as postfix as well like obj++ or obj--.

#include<iostream.h>
class NUM
{
private:
int n;
public:

void getNum(int x)
{
n=x;
}

void dispNum(void)
{
cout << "value of n is: " << n;
}
void operator - (void)
{
n=-n;
}
};

int main()
{
NUM num;
num.getNum(10);
-num;
num.dispNum();
cout << endl;
return 0;

#include<iostream.h>
#include<conio.h>

class complex {
int a, b, c;
public:

complex() {
}

void getvalue() {
cout << "Enter the Two Numbers:";
cin >> a>>b;
}

void operator++() {
a = ++a;
b = ++b;
}

void operator--() {
a = --a;
b = --b;
}
void display() {
cout << a << "+\t" << b << "i" << endl;
}
};

void main() {
clrscr();
complex obj;
obj.getvalue();
obj++;
cout << "Increment Complex Number\n";
obj.display();
obj--;
cout << "Decrement Complex Number\n";
obj.display();
getch();
}
Sample Output
Enter the two numbers: 3 6
Increment Complex Number
4+ 7i
Decrement Complex Number
3+ 6i

Binary Operator Overloading

Binary Operator Overloading in the C++ programming language. An operator which contains
two operands to perform a mathematical operation is called the Binary Operator Overloading.
It is a polymorphic compile technique where a single operator can perform various
functionalities by taking two operands from the programmer or user. There are multiple
binary operators like +, -, *, /, etc., that can directly manipulate or overload the object of a
class.

return_type :: operator binary_operator_symbol (arg)


{
// function definition
}

#include<iostream.h>

class Complex
{
int num1, num2;
public:
void accept()
{
cout<<"\n Enter Two Complex Numbers : ";
cin>>num1>>num2;
}
Complex operator+(Complex obj) //Overloading '+' operator
{
Complex c;
c.num1=num1+obj.num1;
c.num2=num2+obj.num2;
return(c);
}
void display()
{
cout<<num1<<"+"<<num2<<"i"<<"\n";
}
};
int main()
{
Complex c1, c2, sum;
c1.accept();
c2.accept();

sum = c1+c2;
cout<<"\n Entered Values : \n";
cout<<"\t";
c1.display();
cout<<"\t";
c2.display();

cout<<"\n Addition of Real and Imaginary Numbers : \n";


cout<<"\t";
sum.display();
return 0;
}

Type Casting

Type casting refers to the conversion of one data type to another in a program.
Type Casting is divided into two types: Implicit conversion or Implicit Type Casting and
Explicit Type Conversion or Explicit Type Casting.

Implicit Type Casting or Implicit Type Conversion

o It is known as the automatic type casting.


o It automatically converted from one data type to another without any external
intervention such as programmer or user. It means the compiler automatically
converts one data type to another.
o All data type is automatically upgraded to the largest type without losing any
information.
o It can only apply in a program if both variables are compatible with each other.

#include <iostream.h>
int main() {
int num_int = 9;
double num_double;
num_double = num_int;
cout << "num_int = " << num_int << endl;
cout << "num_double = " << num_double << endl;
return 0;
}

Explicit type conversion


Conversions that require user intervention to change the data type of one variable to another,
is called the explicit type conversion. In other words, an explicit conversion allows the
programmer to manually changes or typecasts the data type from one variable to another
type.
#include <iostream>
using namespace std;
int main ()
{
float num2;
int num1 = 25;

num2 = (float) num1;


cout << " The value of int num1 is: " << num1 << endl;
cout << " The value of float num2 is: " << num2 << endl;
return 0;
}

Mutable keyword
Mutable data members are those members whose values can be changed in runtime even if
the object is of constant type. It is just opposite to constant. Sometimes logic required to use
only one or two data member as a variable and another one as a constant to handle the data.
In that situation, mutability is very helpful concept to manage classes.
#include <iostream.h>
class Test {
public:
int a;
mutable int b;
Test(int x=0, int y=0) {
a=x;
b=y;
}
void seta(int x=0) {
a = x;
}
void setb(int y=0) {
b = y;
}
void disp() {
cout<<endl<<"a: "<<a<<" b: "<<b<<endl;
}
};
int main()
{
const Test t(10,20);
cout<<t.a<<" "<<t.b<<"\n";
// t.a=30; //Error occurs because a can not be changed, because object is constant.
t.b=100; //b still can be changed, because b is mutable.
cout<<t.a<<" "<<t.b<<"\n";
return 0;
}

Function Overloading
Function Overloading is defined as the process of having two or more function with the same
name, but different in parameters is known as function overloading in C++. In function
overloading, the function is redefined by using either different types of arguments or a
different number of arguments.

#include <iostream.h>

void SumNum(int A, int B);


void SumNum(int A, int B, int C);
void SumNum(int A, int B, int C, int D);

int main()
{
SumNum(1,2);
SumNum(1,2,3);
SumNum(1,2,3,4);

return 0;
}

void SumNum(int A, int B)


{
cout<< endl << "SUMNUM is : "<< A+B;
}

void SumNum(int A, int B, int C)


{
cout<< endl << "SUMNUM is : "<< A+B+C;
}

void SumNum(int A, int B, int C, int D)


{
cout<< endl << "SUMNUM is : "<< A+B+C+D;
}

Function Overriding
If we inherit a class into the derived class and provide a definition for one of the base class's
function again inside the derived class, then that function is said to be overridden, and this
mechanism is called Function Overriding
class Base
{
public:
void shaow()
{
cout << "Base class\n";
}
};

class Derived:public Base


{
public:
void show()
{
cout << "Derived Class\n";
}
}
int main()
{
Base b; //Base class object
Derived d; //Derived class object
b.show(); //Early Binding Ocuurs
d.show();
}

function overriding vs function overloading

Function Overloading Function Overriding

Functions have same name but different Functions have same name ,same number and
number or different type of parameters. same type of parameters.

Overloading of the functions take place at Overriding of the functions take place at run
compile time. time.

It is also known as compile time It is also known as run time polymorphism.


polymorphism.

The functions that are overloaded are present The functions that are overridden are present
in same class. in different class.

It can occur without inheritance. It cannot occur without inheritance.

Functions can have different data types. Functions should have same data types.

Pointer to base class


That means we can create a pointer variable of a base class and assing the addresses of
derived class object to it.

#include <iostream.h>
class Polygon {
protected:
int width, height;
public:
void set_values (int a, int b)
{ width=a; height=b; }
};

class Rectangle: public Polygon {


public:
int area()
{ return width*height; }
};

class Triangle: public Polygon {


public:
int area()
{ return width*height/2; }
};

int main () {
Rectangle rect;
Triangle trgl;
Polygon * ppoly1 = &rect;
Polygon * ppoly2 = &trgl;
ppoly1->set_values (4,5);
ppoly2->set_values (4,5);
cout<<"\n\tPointers to base class...\n\n";
cout << rect.area() << "\n";
cout << trgl.area() << "\n";
return 0;
}

Virtual function and its significance in c++


o A C++ virtual function is a member function in the base class that you redefine in a
derived class. It is declared using the virtual keyword.
o It is used to tell the compiler to perform dynamic linkage or late binding on the
function.
o There is a necessity to use the single pointer to refer to all the objects of the different
classes. So, we create the pointer to the base class that refers to all the derived objects.
But, when base class pointer contains the address of the derived class object, always
executes the base class function. This issue can only be resolved by using the 'virtual'
function.
o A 'virtual' is a keyword preceding the normal declaration of a function.

#include <iostream.h>
Class A
{
public:
virtual void display()
{
cout << "Base class is invoked"<<endl;
}
};
class B:public A
{
public:
void display()
{
cout << "Derived Class is invoked"<<endl;
}
};
int main()
{
A* a; //pointer of base class
B b; //object of derived class
a = &b;
a->display(); //Late Binding occurs
}

Pure Virtual Function


A pure virtual function is a virtual function in C++ for which we need not to write any
function definition and only we have to declare it. It is declared by assigning 0 in the
declaration.
An abstract class is a class in C++ which have at least one pure virtual function.

● Abstract class can have normal functions and variables along with a pure virtual
function.
● Abstract class cannot be instantiated, but pointers and references of Abstract class type
can be created.
● Abstract classes are mainly used for Upcasting, so that its derived classes can use its
interface.
● If an Abstract Class has derived class, they must implement all pure virtual functions,
or else they will become Abstract too.

virtual void display() = 0;


#include<iostream.h>
class B {
public:
virtual void s() = 0; // Pure Virtual Function
};

class D:public B {
public:
void s() {
cout << "Virtual Function in Derived class\n";
}
};

int main() {
B *b;
D dobj;
b = &dobj;
b->s();
}

Virtual Destructor

A virtual destructor is used to free up the memory space allocated by the derived class object
or instance while deleting instances of the derived class using a base class pointer object. A
base or parent class destructor use the virtual keyword that ensures both base class and the
derived class destructor will be called at run time, but it called the derived class first and then
base class to release the space occupied by both destructors.
#include<iostream>
using namespace std;
class Base
{
public:
Base()
{
cout<< "\n Constructor Base class";
}
~Base()
{
cout<< "\n Destructor Base class";
}
};

class Derived: public Base


{
public:
Derived()
{
cout << "\n Constructor Derived class" ;
}
~Derived() // Destructor function
{
cout << "\n Destructor Derived class" ;
}
};
int main()
{
Base *bptr = new Derived;
delete bptr;
}
Output:

Abstract class.

A class that contains a pure virtual function is known as an abstract class.


1) if a function doesn't have any use in the base class
2) but the function must be implemented by all its derived classes
#include <iostream.h>

class Shape {
protected:
int width;
int height;

public:

virtual int getArea() = 0;


void setWidth(int w)
{
width = w;
}

void setHeight(int h)
{
height = h;
}

};

class Rectangle: public Shape


{
public:
int getArea()
{
return (width * height);
}
};

class Triangle: public Shape {


public:
int getArea()
{
return (width * height)/2;
}
};

int main(void)
{
Rectangle Rect;
Triangle Tri;

Rect.setWidth(5);
Rect.setHeight(7);

cout << "Total Rectangle area: " << Rect.getArea() << endl;

Tri.setWidth(5);
Tri.setHeight(7);

cout << "Total Triangle area: " << Tri.getArea() << endl;

return 0;
}

You might also like