OBJECT ORIENTED
PROGRAMMING
DR. DEEPANWITA DAS
ASSISTANT PROFESSOR
DEPARTMENT OF COMPUTER SCIENCE &
ENGINEERING
NATIONAL INSTITUTE OF TECHNOLOGY, DURGAPUR
CONSTRUCTOR AND DESTRUCTOR
Objectives
•Constructors – introduction and features
•The zero-argument constructor
•Parameterized constructors
•Explicit constructors
•Copy constructor
•Destructors
ACKNOWLEDGEMENT
The contents (figures, concepts, graphics, texts etc.) of the slides are gathered
and utilized from the books mentioned and the corresponding PPTs available
online:
Books:
•Addison Wesley - The C++ Standard Library. A T.
•Competitive Programmer’s Handbook Antti Laakson
•DataStructures_and_Algorithms_in_C++ by Adam Drozdec
•Effective C++ by Scott Meyers
•The C++ Programming Language by Bjarne Stroustrup
• Thinking in Java by Bruce Eckel
• TICPP by Bruce Ekcel
Web References:
1.Programming in C++, Prof. P P Das, NPTEL Video Lectures. Link:
https://nptel.ac.in/noc/courses/noc21/SEM1/noc21-cs02/
2.Compile and Execute C Online (GNU GCC v7.1.1), Link:
https://www.tutorialspoint.com/compile_c_online.php
Disclaimer: The study materials/presentations are solely meant for academic
purposes and they can be reused, reproduced, modified, and distributed by
others for academic purposes only with proper acknowledgements.
The objective to create an user defined data type, such as class that is very similar
to the built in data types.
Say for example: int a=10; \\ both declaration and initialization at the same time.
class student
{ int age;
int roll;
public:
void display()
{
cout<<"Age="<<age;
cout<<"roll="<<roll;
}
void getdata(int x, int y)
{
age=x;
roll=y;
}
};
int main(void)
{
student x;
x.getdata(10, 20);
x.display();
return 0;
}
INTRODUCTION
•So far we saw that, we use member functions
to assign the values to the objects.
x.getdata(10,20);
•Here, after the objects are created, then the
value initialization occurs.
•These member functions can not be used to
initialize the member variables at the time of
creation of the objects.
•C++ provides a special member function that is
used to initialize the objects during their
creation. That is known as the constructor.
•Similarly, another member function is used to
destroy the objects. That is known as
destructors.
CONSTRUCTORS
•The constructor gets called automatically whenever an object of its associated class is created.
•Its name is the same as the class name.
•It is called constructors as its constructs/initializes the objects of the class at the time of their
creation.
For example:
class integer
{
int m,n;
public: integer(void){m=n=0;}
}; if now any object is created it will be initialized automatically.
•It appears as member function of each class, whether it is defined or not.
•It may or may not take parameters.
•It does not return anything (not even void).
•The prototype of a constructor is <class name> (<parameter list>);
•Constructors fulfill the need for a function that guarantees initialization of member data of a
class.
•It allocates space or can set the data members to a default values.
•Domain constraints on the values of data members can also be implemented via constructors.
CONSTRUCTORS
•Consider a class clock having members hours, minutes and seconds.
Clock
{
int hour;
int min;
int sec;
getdata() {hour = 35;} \\ is there any problem?
}
we have domain constraint that hour must have a range from 1 to 24, so if we can program properly
we can retain the domain constraint.
•Consider a class distance having member feet and inches.
•Consider a class DATE having member day, month and year.
DEFAULT CONSTRUCTOR
•Till now we are using this type of statement to create objects: student A;
•On compiling this statement student A; the compiler implicitly converts
this statement as A.student(); and then to student(&A);
•Here also one constructor is called by default which accepts no
parameters.
•That is known as default constructor.
•Ex: student::student() { }
•If no constructor is defined explicitly the compiler supplies default
constructor.
•The default constructor only could perform the storage allocation
(static/dynamic) but no initialization is possible.
•The constructor is a non-static member function.
•It is called for an object.
ZERO ARGUMENT CONSTRUCTOR
#include <iostream>
using namespace std;
class A
{
int x;
public: A(); //our own constructor
};
A::A() //our own constructor
{
cout<<"Constructor of class A
called"<<endl;
}
int main(void)
{
A A1;
cout<<"End of program"<<endl;
return 0;
}
Output
Constructor of class Acalled
End ofprogram
•Constructors are called for every
objects in the similar manner.
•Object are declared or created
before a constructor is called.
•The constructor that does not take any arguments and is called the zero-argument
constructor.
•The constructor provided by default by the compiler also does not take any arguments.
•The terms ‘zero-argument constructor’ and ‘default constructor’ are used interchangeably.
ZERO ARGUMENT CONSTRUCTOR
Now we see that the constructors are
always declared and defined in public
section. What happens if we declare
them in private section?
We can declare the constructors in
any section. But when creating the
object we do it outside of the class
definition.
During object creation constructor is
called but you cannot call any
function from outside the class if that
resides in private.
DEFAULT CONSTRUCTOR
•The constructor is a non-static member function.
•It is called for an object. It, therefore, takes the this pointer as a leading
formal argument.
•The address of the invoking object is passed as a leading
parameter to the constructor call.
•This means that the members of the invoking object can be
accessed from within the definition of the constructor.
•It represents an object that calls a member function.
x.getdata(100,200);
•It points to the object and it is passed automatically to a member
function when it is called.
THIS POINTER
THIS POINTER
PARAMETERIZED CONSTRUCTORS
•Rather than using 0’s we can use other numbers to assign them as a value.
•By passing arguments to the constructor this can be done.
•Constructors take arguments and can, therefore, be overloaded.
•When the constructors take arguments, it is known as the parameterized
constructors.
Example: integer::integer(int x,int y)
{
m=x; n=y;
}
•The parameterized constructor is prototyped and defined just like any other
member function except for the fact that it does not return any value.
•We have to pass the initial values as arguments to the constructor function when
an object is declared.
•Passing parameters can be done in two ways:
✓By calling the constructor explicitly
Ex: integer I=integer(0,100);
✓By calling the constructor implicitly
Ex: integer I(0,100);
•If the parameterized constructor is provided and the zero-argument constructor is
not provided, the compiler will not provide the default constructor. It is mandatory
to define the default constructors if you are using the parameterized constructors.
PARAMETERIZED CONSTRUCTORS
class integer
{
int m,n;
public:
integer(void){ m=n=0;}
integer(int x, int y){ m=x; n=y;}
integer(int p) { m=n=p;}
void display()
{
cout<<"m and n = "<<m<<"and"<<n<<"\n";
}
};
int main(void)
{
integer i1, i3(0,100);
integer i2=integer(20);
i1.display();
i2.display();
i3.display();
return 0;
}
// C++ program to demonstrate constructor overloading
#include <iostream>
using namespace std;
class Room
{
private: double length; double breadth;
public:
// 1. Constructor with no arguments
Room() { length = 6.9; breadth = 4.2; }
// 2. Constructor with two arguments
Room(double l, double b) { length = l; breadth = b; }
// 3. Constructor with one argument Room(double len) { length = len; breadth = 7.2; }
double calculateArea() { return length * breadth; }
};
int main()
{
Room room1, room2(8.2, 6.6), room3(8.2);
cout << "When no argument is passed: " << endl;
cout << "Area of room = " << room1.calculateArea() << endl;
cout << "\nWhen (8.2, 6.6) is passed." << endl;
cout << "Area of room = " << room2.calculateArea() << endl;
cout << "\nWhen breadth is fixed to 7.2 and (8.2) is passed:" << endl;
cout << "Area of room = " << room3.calculateArea() << endl;
return 0;
}
PARAMETERIZED CONSTRUCTORS
INITIALIZING AN OBJECT FROM ANOTHER
OBJECT
int x=10; // initializing x with a value
int y=x; //initializing y with the value of x
Can we do stack s1=s2? We are trying to create object by copying another object.
Is there any constructor which
can construct x3 by copying x2?
Here, A default copy constructor is
invoked by the compiler,
automatically.
Bit wise copy of x2 to x3 done
10
a=10
ptr
x1
20
a=20
ptr
x2 Due to bitwise copying, x3 basically
is initialized by the address of the old
object x2 and they both points to the
same location.
20
a=20
ptr
x2
a=20
ptr
x3
25
a=20
ptr
a=20
ptr
X3.fb(25)x2
So we need
to write an
explicit copy
constructor
for solving
this
Copy constructor initializes the objects during their creation by using/copying the
values of another objects of its own class.
These two are same:
xyz x3=x2;
xyz x4(x2);
Trying to write the explicit copy constructor:
xyz::xyz(xyz x)
{
}
This will not work as when x2 is passed (called by value) then x2 is copied to x, for
that again copy constructor will be called and so on the repetition.
So we need to pass the reference of the object. xyz::xyz(xyz &x) { ….}
Ex: class A{
-------------
public: A(A);
};
This is Wrong
class A{
-------------
public: A(A&);
};
This is correct.
COPY CONSTRUCTOR
COPY CONSTRUCTOR
•The copy constructor is a special type of parameterized constructor
which copies one object to another.
•It is called when an object is created and equated to an existing
object at the same time.
•The copy constructor is called for the object being created. The pre-
existing object is passed as a parameter to it.
•The copy constructor member-wise copies the object passed as a
parameter to it into the object for which it is called.
•The object whose reference is passed is protected from accidental
changes by const keyword.
xyz::xyz(const xyz &x) { ….}
or
xyz::xyz(xyz const &x) { ….}
COPY CONSTRUCTOR
xyz::xyz(const xyz &x) { ….}
or
xyz::xyz(xyz const &x) { ….}
•When you pass an object by reference (e.g., void func(MyObject& obj)), the
function can potentially modify the original object.
•Adding const to the reference parameter (e.g., void func(const MyObject&
obj)) explicitly declares that the function will not modify the object it receives.
•This enforces immutability within the function's scope, preventing unintended
side effects and making the code safer and easier to reason about. If the
function attempts to modify the const reference, the compiler will issue an
error.
20
xyz::xyz(const xyz &x)
{
cout<<“copy constructor”<<endl;
ptr = new int[x.a];
a=x.a;
for(int i=0; i<a;i++)
ptr[i]=x.ptr[i];
}
a=20
ptr
x2
a=20
ptr
x3
X2 is passed to x
20
Instead of bitwise copying or shallow copying this
is known as deep copying
Bitwise Copying Shallow Copying (Default choice in object to object copy)
Here the contents (address value) of the pointer member of the existing object is also copied to
the pointer member of the newly constructed object; thereby both object pointers points to the
same dynamically allocated location in the heap instead of having individual copies.
Side effect:
•If any one object modifies the memory in heap it points the other objects state also gets
affected
•If any one object goes out of the scope its destructor call might to deallocate the space in
heap resulting the other object now pointing to garbage.
Solution Deep Copying (Write a explicit copy constructor)
This explicitly written constructor will separately allocate space for the new object and will copy
the existing object heap contents to its heap allocate space, thereby both objects will have
individual copies of the dynamically allocated space, too.
Original
object
Cloned
object
Reference
space in heap
Original
object
Cloned
object
Reference
space in heap
Reference
space in heap
Default copy constructor
Shallow copy
Copy constructor
(Deep Copy)
COPY CONSTRUCTOR
class integer{
int m,n;
public: integer(void){ m=n=0;}
integer(int x, int y){ m=x; n=y;}
integer(integer &i) { m=i.m;
n=i.n;}
};
int main(void)
{
integer i1, i2(10,20);
integer i3(i2);
return 0;
}
#include <iostream>
using namespace std;
class Box
{ private:
double length;
double breadth;
double height;
double volume;
public:
Box () {}
Box(double h, double l, double b )
{height=h; length=l; breadth=b;}
Box(double h, double l, int b = 5)
{height=h; length=l; breadth=b;}
Box (Box &x) { height=x.height; length=x.length; breadth=x.breadth;}
DESTRUCTORS
•It is used to destroy the objects that have been created by a
constructor.
•Deallocates space that is allocated by the constructors and reset the
default values.
•Its name is same as constructor but preceded by a tilde.
•Ex: ~integer() { }
•A destructor never passes or returns any arguments.
•It is called implicitly by compiler during exit of the program.
•Destructors can not be overloaded.
•Destructors may be called even if there is no user defined
constructors defined explicitly.
•Good programming practice to use own destructors for every
program to deallocate memory after use.
DESTRUCTORS
int count =0;
class alpha {
public: alpha()
{ count++;
cout<<"No of object created = "<<count <<"\n";
}
~alpha()
{
cout<<"No of object destroyed="<<count<<"\n";
count --;
}
};
int main(void)
{
cout<<"\n Enter main";
alpha A1,A2, A3, A4;
{
cout<<"\n Enter block 1";
alpha A5;
}
{
cout<<"\n Enter block 2";
alpha A6;
}
cout<<"\n Re- Enter main";
return 0;
}
Output:
No. of object created = 1
No. of object created = 2
No. of object created = 3
No. of object created = 4
Enter block1
No. of object created = 5
No. of object destroyed = 5
Enter block2
No. of object created = 5
No. of object destroyed = 5
Re- Enter Main
No. of object destroyed = 4
No. of object destroyed = 3
No. of object destroyed = 2
No. of object destroyed = 1