5 Classes & Objects – II
Jyoti Pareek
In the previous module we have seen that the Classes are basic building blocks of object oriented applications. A well-crafted class can create powerful user defined data type. Whenever we need to store information of that data type, we create variable of that data type or object of that data type. Data members can be private or public. Private members can be accessed only by member functions. Public members can be accessed outside the class through object of the class using dot operator. Whenever we create an object of any class, each object is allocated memory for each data member. For example have a look at the following program.
Need of Static Data Members
When we read data from the user in these objects, objects will be holding data (assumed to be given by the user) as follows
You will notice here that rollno, name and marks_obtained will have different values in each object as each student has different rollno and name and each will obtain different marks. But total_marks remain same for each student. You would notice that even when total_marks are same for all, they are stored in each student object. This results in memory wastage. Also this unnecessary repetition of total_marks has other problems. If we want to change the value of total_marks, even though it is common value for all, we will have to modify them separately for all objects as follows :
Also if we forget to change value of total_marks in one of the objects, it will result into data inconsistency as shown below. If we attempt to compute percentage of marks obtained by the students.The students whose total_marks did not get modified and remained 50, will be at disadvantage as correct percentage will not be calculated.
Static Data Members
We can define data member of a class as static using static keyword static.
A static data member is shared by all objects of the class. There is only one copy of the static member. All static data is initialized to zero when the first object is created, if no other initialization is present. We cannot initialize in the class definition but it can be initialized outside the class.
class student
{
int rollno;
char name[20];
int marks_obtained;
static int total_marks;
public :
void readdata();
void displaydata();
int computePercentage();
int update_totalmarks(int mks) { total_marks = mks;}
};
// Initialize static data member int student :: total_marks = 0;
The advantage of having one copy is that whenever the value of static data member needs to be modified, we need to modify it at one place only as there is only one copy of the same.
As we can see in the above program that the modification is done only once as there is only one common copy of the same. We need to invoke update_totalmarks() function on any of the objects. In the above program we have invoked this function on object stud1. We do not wish to update total marks for object 1 only, but we have invoked it on stud1 object as being a member function, it needs any object for its invocation. We could have invoked it on stud2 or stud3 as well. Invokation of update_totalmarks() on stud1 doesn’t look logical, and gives impression that we wish to modify total marks of stud1. What can we do to make function invocation look more logical and convincing?
Well as we can define data members as static, we can also define member functions static. Defining update_totalmarks() as static can remove the need of calling update_totalmarks() on any object.
Static Members Function
A member function in a class can be declared as static. A static member function has certain special characteristics. These are:
· A static function can have access to only other static members.
· A static member function can be accessed not only by the object name but also with the class name.
Following program illustrates the use of static data member:
class student
{
int rollno;
char name[20];
int marks_obtained;
static int total_marks;
public :
void readdata();
void displaydata();
int computePercentage();
static int update_totalmarks(int mks) { total_marks = mks;}
};
- // Initialize static data member int student :: total_marks = 0;
As in the above program, we have declared update_totalmarks() as static, we need not invoke it on any object. It can be invoked by qualifying its call with class as follows :
Public Static Data Members
Static data member can also be declared as public.
class student
{
int rollno;
char name[20];
int marks_obtained;
public :
static int total_marks;
// public static member
void readdata();
void displaydata();
int computePercentage();
static int update_totalmarks(int mks) { total_marks = mks;}
};
// Initialize static data member int student :: total_marks = 0;
In this case static member can be accessed outside the class without object as follows :
Advantage of Static Data Members
Following are the advantages of using Static Data members
- Only one copy of the data which is common for all the objects of that class is made
- As there is only one copy of the data , Updation needs to be done at one place only once
- Removes the possibility of data inconsistency
Nested Classed
A nested class is a class which is declared in another enclosing class. A nested class is a member and as such has the same access rights as any other member. The members of an enclosing class have no special access to members of a nested class; the usual access rules shall be obeyed.
Following program illustrates defining nested classes :
class | student | ||
{ | |||
int rollno; | |||
char name[20]; | |||
int marks_obtained; | |||
static int total_marks; | |||
class Time | |||
{ | |||
int hours; | |||
int minute; | |||
int seconds; | |||
public : | |||
void readTime(); | |||
void displayTime(); | |||
time differenceTime(Time t); | |||
time addTime(Time t); | |||
} dob; | |||
public : | |||
void readdata(); | |||
{ | |||
cin >> rollno; | |||
cin >> name; | |||
cin >> marks_obtained; | |||
cin >> dob.hours; | // will not work | ||
dob.readTime(); | |||
} | |||
void displaydata(); | |||
{ | |||
cout << rollno; | |||
cout << name; | |||
cout << marks_obtained; | |||
cout << dob.hours; | // will not work | ||
dob.displayTime(); | |||
} | |||
int | computePercentage(); |
static int update_totalmarks(int mks) { total_marks = mks;}
};
int student :: total_marks = 0;
In the above program class is declared inside the student Class.
Limitation of Nested Classed
The limitation of the nested class is that ists object can only be created inside the enclosing class. Its definition is not available outside the class. The same is illustrated using following example
class student
{
int rollno;
char name[20];
int marks_obtained;
static int total_marks;
class Time
{
int hours;
int minute;
int seconds;
public :
void readTime();
void displayTime();
time differenceTime(Time t);
time addTime(Time t);
} dob;
void readdata();
void displaydata();
int computePercentage();
static int update_totalmarks(int mks) { total_marks = mks;}
};
int student :: total_marks = 0;
void main()
{
Time current_time; // | will not work; | ||
…………………………… | |||
………………………….. | |||
…………………………. |
}
We can see in the above program that the object of time class cannot be created in main() function as its definition is local to the student class and is not available outside the student class.
Object as a Data Member
A class can also have object of another class as data members. Limitation of nested class can be overcome by defining Time class outside the student class, and declare the object of Time class as one of the data members of student class. Following program illustrates the same:
class Time
{
int hours;
int minute;
int seconds;
public :
void readTime();
void displayTime();
time differenceTime(Time t);
time addTime(Time t);
};
class student
{
int rollno;th
char name[20];
int marks_obtained;
static int total_marks;
Time dob;
public :
void readdata();
{
cin >> rollno;
cin >> name;
cin >> marks_obtained;
dob.readTime();
}
void displaydata();
{
cout << rollno;
cout << name;
cout << marks_obtained;
dob.displayTime();
}
int computePercentage();
static int update_totalmarks(int mks) { total_marks = mks;}
};
int student : : total_marks = 0;
void function demo()
{
Time t; // will Work;
..…………………….
………………………
}
Local Classes
We can also define Class inside any function. But when we do so, such class becomes local to that function. The definition of such class will only be available to the class in which it has been defined and object of this class cannot be defined outside this function. Following program defines class time inside main() function.
void main()
{
class Time
{
int hours;
int minutes;
int seconds;
void readTime();
void displayTime();
time differenceTime(time t);
}
Time current_time;
current_time.hours = 3;
current_time.minutes= 20;
current_time.seconds = 35;
current_time.displayTime();
}
void main()
{
class Time
{
int hours;
int minutes;
int seconds;
void readTime();
void displayTime();
time differenceTime(time t);
}
Time current_time;
current_time.hours = 3;
current_time.minutes= 20;
current_time.seconds = 35;
current_time.displayTime();
}
void function demo()
{
Time t; // will not Work;
..…………………….
………………………
………………………
}
You can see in above program, class Time is defined inside the main() function. Therefore it becomes local to the main() function, and its definition is not available outside the main() function. Hence its object cannot be created in another function demo(). It is advisable that the datatype implemented through class should be defined globally and objects of that class must be defined locally.
Defining Class Globally
Following program defines the class Time globally, rather than declaring as local to main().
class Time
{
int hours;
int minutes;
int seconds;
void readTime();
void displayTime();
time differenceTime(time t);
}
void main()
{
Time current_time;
current_time.hours = 3;
current_time.minutes= 20;
current_time.seconds = 35;
current_time.displayTime();
}
void function demo()
{
Time t; // will Work;
..…………………….
………………………
………………………
}
Summary
- We can define class members static using static keyword. A static member is shared by all objects of the class. There is only one copy of the static member.
- Defining common data members as static help save memory, makes modification simple and consistant.
- We can define classes inside another class(nested class) and inside function(local class). But it is better to define class globally.
you can view video on Classes & Objects -II |
Additional References
1) Stanley Lippmann, “C++ Primer”, Pearson Education.
2) Bjarne Stroustrup, “The C++ Programming Language”, Pearson Education.
3) Scott Mayer, “Effective C++”, Addison Wesley.
4) Bhushan Trivedi , Programming with ANSI C++, 2/e , Oxford University Press.
5) Yashavant P. Kanetkar “Let Us C++” , Bpb Publications.
6) Abhiram G. Ranade, “An Introduction to Programming through C++” , McGraw Hill
7) Ellis and B. Stroustrup “Annotated C++ Reference Manual”, http://www.stroustrup.com/arm.html
8) Herbert Schildt, “Complete Reference C++”, McGraw Hill Publications.
9) Ashok Kamthane, “Object Oriented Programming with ANSI and Turbo C++”, Pearson Education
10) E Balaguruswami, “Object Oriented Programming With C++”, Tata McGraw Hill
11) “C++ FAQs”, Pearson Education.