[go: up one dir, main page]

0% found this document useful (0 votes)
127 views36 pages

C++ - Chapter 3

This document discusses operator overloading, inheritance, and polymorphism in C++. It defines operator overloading as extending the meaning of operators to user-defined types. It lists which operators can and cannot be overloaded. It also discusses the syntax and rules for overloading unary and binary operators. The document then defines inheritance as a class deriving properties from another class. It provides an example to illustrate code reuse through inheritance. Finally, it discusses the different types of inheritance in C++.
Copyright
© © All Rights Reserved
We take content rights seriously. If you suspect this is your content, claim it here.
Available Formats
Download as PDF, TXT or read online on Scribd
0% found this document useful (0 votes)
127 views36 pages

C++ - Chapter 3

This document discusses operator overloading, inheritance, and polymorphism in C++. It defines operator overloading as extending the meaning of operators to user-defined types. It lists which operators can and cannot be overloaded. It also discusses the syntax and rules for overloading unary and binary operators. The document then defines inheritance as a class deriving properties from another class. It provides an example to illustrate code reuse through inheritance. Finally, it discusses the different types of inheritance in C++.
Copyright
© © All Rights Reserved
We take content rights seriously. If you suspect this is your content, claim it here.
Available Formats
Download as PDF, TXT or read online on Scribd
You are on page 1/ 36

Unit-III: Operator Overloading, Inheritance &

Polymorphism

3.1 Concept of Operator Overloading


Operator overloading is an important concept in C++.
It is a type of polymorphism in which an operator is
overloaded to give user defined meaning to it.
Overloaded operator is used to perform operation on user-
defined data type.
For example '+' operator can be overloaded to perform
addition on various data types, like for Integer,
String(concatenation) etc.

Almost any operator can be overloaded in C++. However


there are few operator which can not be overloaded.
Operator that are not overloaded are follows
-scope operator - ::
-sizeof
-member selector - .
-member pointer selector - *
-ternary operator - ?:
Operator Overloading Syntax
1|P a ge
Implementing Operator Overloading in C++
Operator overloading can be done by implementing a
function which can be :
1.Member Function
2.Non-Member Function
3.Friend Function
Operator overloading function can be a member function if
the Left operand is an Object of that class, but if the Left
operand is different, then Operator overloading function
must be a non-member function.
Operator overloading function can be made friend function
if it needs access to the private and protected members of
class.

3.2 Rules for Overloading


Although it looks simple to redefine the operators in
operator overloading, there are certain restrictions and
limitation in overloading the operators.
Some of them are listed below:
1. Only existing operators can be overloaded. New
operators cannot be overloaded.

2|P a ge
2. The overloaded operator must have at least one operand
that is of user defined type.
3. We cannot change the basic meaning of an operator.
That is to say, We cannot redefine the plus(+) operator to
subtract one value from the other.
4. Overloaded operators follow the syntax rules of the
original operators. They cannot be overridden.
5. There are some operators that cannot be overloaded like
size of operator(sizeof), membership operator(.), pointer to
member operator(.*), scope resolution operator(::),
conditional operators(?:) etc
6. We cannot use “friend” functions to overload certain
operators.However, member function can be used to
overload them. Friend Functions can not be used with
assignment operator(=), function call operator(()),
subscripting operator([]), class member access operator(->)
etc.
7. Unary operators, overloaded by means of a member
function, take no explicit arguments and return no explicit
values, but, those overloaded by means of a friend function,
take one reference argument (the object of the relevent
class).
8. Binary operators overloaded through a member function
take one explicit argument and those which are overloaded
through a friend function take two explicit arguments.
9. When using binary operators overloaded through a
member function, the left hand operand must be an object
of the relevant class.

3|P a ge
10. Binary arithmetic operators such as +,-,* and / must
explicitly return a value. They must not attempt to change
their own arguments.

3.3 Unary & Binary operator overloading


Unary Operators Overloading in C++
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--.
Example1: ++ Operator (Unary Operator) Overloading
// Overload ++ when used as prefix

#include <iostream>
using namespace std;

class Count {
private:
int value;

public:

// Constructor to initialize count to 5


4|P a ge
Count() : value(5) {}

// Overload ++ when used as prefix


void operator ++ () {
++value;
}

void display() {
cout << "Count: " << value << endl;
}
};

int main() {
Count count1;

// Call the "void operator ++ ()" function


++count1;

count1.display();
return 0;
}
Output:
Count: 6
Here, when we use ++count1;, the void operator ++ () is
called.
This increases the value attribute for the object count1 by 1.

5|P a ge
Binary Operators Overloading in C++
The binary operators take two arguments and following are
the examples of Binary operators.
You use binary operators very frequently like addition (+)
operator, subtraction (-) operator and division (/) operator.
Example 4: C++ Binary Operator Overloading

// C++ program to overload the binary operator +


// This program adds two complex numbers

#include <iostream>
using namespace std;

class Complex {
private:
float real;
float imag;

public:
// Constructor to initialize real and imag to 0
Complex() : real(0), imag(0) {}

void input() {
cout << "Enter real and imaginary parts respectively: ";
cin >> real;
cin >> imag;
}

// Overload the + operator


6|P a ge
Complex operator + (const Complex& obj) {
Complex temp;
temp.real = real + obj.real;
temp.imag = imag + obj.imag;
return temp;
}

void output() {
if (imag < 0)
cout << "Output Complex number: " << real <<
imag << "i";
else
cout << "Output Complex number: " << real << "+"
<< imag << "i";
}
};

int main() {
Complex complex1, complex2, result;

cout << "Enter first complex number:\n";


complex1.input();

cout << "Enter second complex number:\n";


complex2.input();

// complex1 calls the operator function


// complex2 is passed as an argument to the function
result = complex1 + complex2;
7|P a ge
result.output();

return 0;
}
Output:
Enter first complex number:
Enter real and imaginary parts respectively: 9 5
Enter second complex number:
Enter real and imaginary parts respectively: 7 6
Output Complex number: 16+11i

3.4 Concept of Inheritance


The capability of a class to derive properties and
characteristics from another class is called Inheritance.
Inheritance is one of the most important feature of Object
Oriented Programming.
Sub Class: The class that inherits properties from another
class is called Sub class or Derived Class.
Super Class:The class whose properties are inherited by
sub class is called Base Class or Super class.
Consider a group of vehicles.
You need to create classes for Bus, Car and Truck.
The methods fuelAmount(), capacity(), applyBrakes() will
be same for all of the three classes.
If we create these classes avoiding inheritance then we
have to write all of these functions in each of the three
classes as shown in below figure:

8|P a ge
You can clearly see that above process results in
duplication of same code 3 times.
This increases the chances of error and data redundancy.
To avoid this type of situation, inheritance is used.
If we create a class Vehicle and write these three functions
in it and inherit the rest of the classes from the vehicle
class, then we can simply avoid the duplication of data and
increase re-usability.
Look at the below diagram in which the three classes are
inherited from vehicle class:

Using inheritance, we have to write the functions only one


time instead of three times as we have inherited rest of the
three classes from base class(Vehicle).
9|P a ge
Advantage of C++ Inheritance
Code reusability: Now you can reuse the members of your
parent class. So, there is no need to define the member
again. So less code is required in the class.

Implementing inheritance in C++:


For creating a sub-class which is inherited from the base
class we have to follow the below syntax.
Syntax:
class subclass_name : access_mode base_class_name
{
//body of subclass
};
Here, subclass_name is the name of the sub class,
access_mode is the mode in which you want to inherit this
sub class for example: public, private etc. and
base_class_name is the name of the base class from which
you want to inherit the sub class.
Modes of Inheritance
Public mode: If we derive a sub class from a public base
class. Then the public member of the base class will
become public in the derived class and protected members
of the base class will become protected in derived class.
Protected mode: If we derive a sub class from a Protected
base class. Then both public member and protected
members of the base class will become protected in derived
class.

10 | P a g e
Private mode: If we derive a sub class from a Private base
class. Then both public member and protected members of
the base class will become Private in derived class.
We can summarize the different access types according to -
who can access them in the following way –
Access public protected private

Same class yes yes yes

Derived classes yes yes no

Outside classes yes no no

3.5 Types of Inheritance


C++ supports five types of inheritance:
1.Single inheritance
2.Multiple inheritance
3.Hierarchical inheritance
4.Multilevel inheritance
5.Hybrid inheritance

11 | P a g e
1. Single Inheritance:
In single inheritance, a class is allowed to inherit from only
one class. i.e. one sub class is inherited by one base class
only.

Syntax:
class subclass_name : access_mode base_class
{
//body of subclass
};

12 | P a g e
// C++ program to explain Single inheritance
#include <iostream>
using namespace std;

// base class
class Vehicle {
public:
Vehicle()
{
cout << "This is a Vehicle" << endl;
}
};

// sub class derived from two base classes


class Car: public Vehicle{

};

// main function
int main()
{
// creating object of sub class will
// invoke the constructor of base classes
Car obj;
return 0;
}
Output:
This is a vehicle

13 | P a g e
2.Multiple Inheritance:
Multiple Inheritance is a feature of C++ where a class can
inherit from more than one classes. i.e one sub class is
inherited from more than one base classes.

Syntax:
class subclass_name : access_mode base_class1,
access_mode base_class2, ....
{
//body of subclass
};
Here, the number of base classes will be separated by a
comma (‘, ‘) and access mode for every base class must be
specified.
// C++ program to explain multiple inheritance
#include <iostream>
using namespace std;

// first base class


class Vehicle {
public:
Vehicle()

14 | P a g e
{
cout << "This is a Vehicle" << endl;
}
};

// second base class


class FourWheeler {
public:
FourWheeler()
{
cout << "This is a 4 wheeler Vehicle" << endl;
}
};

// sub class derived from two base classes


class Car: public Vehicle, public FourWheeler {

};
// main function
int main()
{
// creating object of sub class will
// invoke the constructor of base classes
Car obj;
return 0;
}
Output:
This is a Vehicle
This is a 4 wheeler Vehicle
15 | P a g e
3.Multilevel Inheritance:
In this type of inheritance, a derived class is created from
another derived class.

// C++ program to implement Multilevel Inheritance


#include <iostream>
using namespace std;

// base class
class Vehicle
{
public:
Vehicle()
{
cout << "This is a Vehicle" << endl;
}
};

16 | P a g e
class fourWheeler: public Vehicle
{ public:
fourWheeler()
{
cout<<"Objects with 4 wheels are vehicles"<<endl;
}
};
// sub class derived from two base classes
class Car: public fourWheeler{
public:
car()
{
cout<<"Car has 4 Wheels"<<endl;
}
};

// main function
int main()
{
//creating object of sub class will
//invoke the constructor of base classes
Car obj;
return 0;
}
output:
This is a Vehicle
Objects with 4 wheels are vehicles
Car has 4 Wheels

17 | P a g e
4.Hierarchical Inheritance:
In this type of inheritance, more than one sub class is
inherited from a single base class. i.e. more than one
derived class is created from a single base class.

// C++ program to implement Hierarchical Inheritance


#include <iostream>
using namespace std;

// base class
class Vehicle
{
public:
Vehicle()
{
cout << "This is a Vehicle" << endl;
}
};

// first sub class


18 | P a g e
class Car: public Vehicle
{

};

// second sub class


class Bus: public Vehicle
{

};

// main function
int main()
{
// creating object of sub class will
// invoke the constructor of base class
Car obj1;
Bus obj2;
return 0;
}
Output:
This is a Vehicle
This is a Vehicle

5.Hybrid (Virtual) Inheritance:


Hybrid Inheritance is implemented by combining more
than one type of inheritance.
For example: Combining Hierarchical inheritance and
Multiple Inheritance.
19 | P a g e
Below image shows the combination of hierarchical and
multiple inheritance:

// C++ program for Hybrid Inheritance

#include <iostream>
using namespace std;

// base class
class Vehicle
{
public:
Vehicle()
{
cout << "This is a Vehicle" << endl;
}
};

//base class
20 | P a g e
class Fare
{
public:
Fare()
{
cout<<"Fare of Vehicle\n";
}
};

// first sub class


class Car: public Vehicle
{

};

// second sub class


class Bus: public Vehicle, public Fare
{

};

// main function
int main()
{
// creating object of sub class will
// invoke the constructor of base class
Bus obj2;
return 0;
}
21 | P a g e
Output:
This is a Vehicle
Fare of Vehicle

3.6 Concept of Polymorphism


The term "Polymorphism" is the combination of "poly" +
"morphs" which means many forms.
It is a greek word.
In simple words, we can define polymorphism as the ability
of a message to be displayed in more than one form.
A real-life example of polymorphism, a person at the same
time can have different characteristics.
Like a man at the same time is a father, a husband, an
employee.
So the same person posses different behavior in different
situations. This is called polymorphism.
Polymorphism is considered as one of the important
features of Object Oriented Programming.
In C++ polymorphism is mainly divided into two types:
1.Compile time Polymorphism
2.Runtime Polymorphism

22 | P a g e
1.Compile time polymorphism:
This type of polymorphism is achieved by function
overloading or operator overloading.
Function Overloading:
When there are multiple functions with same name but
different parameters then these functions are said to be
overloaded.
Functions can be overloaded by change in number of
arguments or/and change in type of arguments.
Operator Overloading:
C++ also provide option to overload operators.
For example, we can make the operator (‘+’) for string
class to concatenate two strings.
We know that this is the addition operator whose task is to
add two operands.

23 | P a g e
So a single operator ‘+’ when placed between integer
operands , adds them and when placed between string
operands, concatenates them.

2.Runtime polymorphism:
This type of polymorphism is achieved by Function
Overriding.
Function overriding on the other hand occurs when a
derived class has a definition for one of the member
functions of the base class.
That base function is said to be overridden.
// C++ program for function overloading
#include <bits/stdc++.h>

using namespace std;


class Geeks
{
public:

// function with 1 int parameter


void func(int x)
{
cout << "value of x is " << x << endl;
}

// function with same name but 1 double parameter


void func(double x)
{
cout << "value of x is " << x << endl;
24 | P a g e
}

// function with same name and 2 int parameters


void func(int x, int y)
{
cout << "value of x and y is " << x << ", " << y <<
endl;
}
};

int main() {

Geeks obj1;

// Which function is called will depend on the parameters


passed
// The first 'func' is called
obj1.func(7);

// The second 'func' is called


obj1.func(9.132);

// The third 'func' is called


obj1.func(85,64);
return 0;
}
Output:
value of x is 7
value of x is 9.132
25 | P a g e
value of x and y is 85, 64
In the above example, a single function named func acts
differently in three different situations which is the property
of polymorphism.

3.7 Virtual Base Classes


Virtual base classes are used in virtual inheritance in a way
of preventing multiple “instances” of a given class
appearing in an inheritance hierarchy when using multiple
inheritances.
Need for Virtual Base Classes:
Consider the situation where we have one class A.
This class is A is inherited by two other classes B and C.
Both these class are inherited into another in a new class D
as shown in figure below.

26 | P a g e
As we can see from the figure that data members/function
of class A are inherited twice to class D.
One through class B and second through class C.
27 | P a g e
When any data / function member of class A is accessed by
an object of class D, ambiguity arises as to which
data/function member would be called? One inherited
through B or the other inherited through C.
This confuses compiler and it displays error.
Syntax for Virtual Base Classes:
Syntax 1:
class B : virtual public A
{
};

Syntax 2:
class C : public virtual A
{
};
Example
#include <iostream>
using namespace std;

class A {
public:
int a;
A() // constructor
{
a = 10;
}
};

class B : public virtual A {


28 | P a g e
};

class C : public virtual A {


};

class D : public B, public C {


};

int main()
{
D object; // object creation of class d
cout << "a = " << object.a << endl;

return 0;
}
Output:
a = 10
Explanation :The class A has just one data member a which
is public.
This class is virtually inherited in class B and class C.
Now class B and class C becomes virtual base class and no
duplication of data member a is done.

29 | P a g e
3.8 Pointer to Derived class
We can use pointers not only to the base objects but also to
the objects of derived classes.
Pointers to objects of a base class are type-compatible with
pointers to objects of a derived class.
Therefore, a single pointer variable can be made to point to
objects belonging to different classes.
For example, if B is a base class and D is a derived class
from B, then a pointer declared as a pointer to B can also be
a pointer to D.
Consider the following declarations:
B *cptr; //pointer to class B type variable
B b; //base object
D d; //derived object
cptr = &b; //cptr points to object b
We can make cptr to point to the object d as follows:
Cptr = &d //cptr points to object d
This is perfectly valid with C++ because d is an object
derived from the class B.
However, there is a problem in using cptr to access the
public members of the derived class D.
Using cptr, we can access only those members which are
inherited from B and not the members that originally
belong to D.
In case a member of D has the same name as one of the
members of B, then any references to that member by cptr
will always access the base class member.

30 | P a g e
Although C++ permits a base pointer to point to any object
derived from that base, the pointer cannot be directly used
to access all the members of the derived class.
We may have to use another pointer declared as pointer to
the derived type.
Example:
#include<iostream.h>
class base
{
public:
int n1;
void show()
{
cout<<”\nn1 = “<<n1;
}
};
class derive : public base
{
public:
int n2;
void show()
{
cout<<”\nn1 = “<<n1;
cout<<”\nn2 = “<<n2;
}
};
int main()
{
base b;
31 | P a g e
base *bptr; //base pointer
cout<<”Pointer of base class points to it”;
bptr=&b; //address of base class
bptr->n1=44; //access base class via base pointer
bptr->show();
derive d;
cout<<”\n”;
bptr=&d; //address of derive class
bptr->n1=66; //access derive class via base
pointer
bptr->show();
return 0;
}
Output
Pointer of base class points to it
n1 = 44
Pointer of base class points to derive class
n1=66

32 | P a g e
3.9 Virtual functions and Rules for Virtual function
A virtual function is a member function which is declared
within a base class and is re-defined(Overriden) by a
derived class.
When you refer to a derived class object using a pointer or
a reference to the base class, you can call a virtual function
for that object and execute the derived class’s version of the
function.
-Virtual functions ensure that the correct function is called
for an object, regardless of the type of reference (or
pointer) used for function call.
-They are mainly used to achieve Runtime polymorphism
-Functions are declared with a virtual keyword in base
class.
-The resolving of function call is done at Run-time.

Rules for Virtual Functions


1.Virtual functions cannot be static and also cannot be a
friend function of another class.
2.Virtual functions should be accessed using pointer or
reference of base class type to achieve run time
polymorphism.
3.The prototype of virtual functions should be same in base
as well as derived class.
4.They are always defined in base class and overridden in
derived class. It is not mandatory for derived class to
override (or re-define the virtual function), in that case base
class version of function is used.

33 | P a g e
5.A class may have virtual destructor but it cannot have a
virtual constructor.
C++ virtual function Example
#include <iostream>
{
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
}
Output:
Derived Class is invoked

34 | P a g e
3.10 Pure Virtual functions
A pure virtual function (or abstract function) in C++ is a
virtual function for which we don’t have implementation,
we only declare it.
A pure virtual function is declared by assigning 0 in
declaration.
A virtual function is not used for performing any task. It
only serves as a placeholder.
When the function has no definition, such function is
known as "do-nothing" function.
The "do-nothing" function is known as a pure virtual
function.
A pure virtual function is a function declared in the base
class that has no definition relative to the base class.
A class containing the pure virtual function cannot be used
to declare the objects of its own, such classes are known as
abstract base classes.
The main objective of the base class is to provide the traits
to the derived classes and to create the base pointer used for
achieving the runtime polymorphism.
Pure virtual function can be defined as:
virtual void display() = 0;
Example:
#include <iostream>
using namespace std;
class Base
{
public:

35 | P a g e
virtual void show() = 0;
};
class Derived : public Base
{
public:
void show()
{
std::cout << "Derived class is derived from the base
class." << std::endl;
}
};
int main()
{
Base *bptr;
//Base b;
Derived d;
bptr = &d;
bptr->show();
return 0;
}
Output:
Derived class is derived from the base class.

36 | P a g e

You might also like