CSC166 · Exam intelligence
Object Oriented Programming important questions
From 6 past TU papers: which questions keep coming back, how much they carry, and what is most likely to show up next. Every question links to a model answer.
Most likely in the next examStatistical
Ranked by how often a topic is asked, its marks weight, and whether it is due after skipping the 2080.1 paper. No guarantees; study the whole syllabus.
1asked 6xavg 6 marks · due (skipped 2080.1) · FunctionsAnswerHideWhen inline functions may not work? Define and write syntax for default arguments. Write a program to display N number of characters by using default arguments for both parameters. Assume that the function takes two arguments, one character to be printed and other how many times the character to be printed respectively.[10]
When inline functions may not work? Define and write syntax for default arguments. Write a program to display N number of characters by using default arguments for both parameters. Assume that the function takes two arguments, one character to be printed and other how many times the character to be printed respectively.[10]
Answer: Inline Functions, Default Arguments, and Program
Part 1: When Inline Functions May NOT Work (3 marks)
The compiler may ignore the inline request and treat the function as a normal function in the following situations:
-
Function contains loops - If the inline function contains looping statements such as
for,while, ordo-while, the compiler will not inline it. -
Function contains static variables - If the function has static local variables declared inside it, it cannot be inlined.
-
Function is recursive - A recursive inline function (a function that calls itself) cannot be expanded inline.
-
Function contains switch or goto statements - Functions containing
switchorgotocontrol statements may not be inlined. -
Function is too large/complex - If the function body is too large, inlining it would increase code size significantly, so the compiler refuses to inline it.
-
Function returns a value and contains multiple return statements - In some cases, multiple return points prevent inlining.
Note: The
inlinekeyword is only a request to the compiler, not a command. The compiler has the final decision.
Part 2: Default Arguments - Definition and Syntax (3 marks)
Definition:
A default argument is a value provided in a function declaration that is automatically assigned by the compiler if the calling function does not provide a value for that argument. It allows a function to be called with fewer arguments than it is defined to accept.
Key Rules:
- Default arguments must be specified from right to left (trailing arguments first).
- Once a default value is assigned to a parameter, all parameters to its right must also have default values.
- Default values are specified in the function declaration (prototype).
Syntax:
return_type function_name(datatype param1, datatype param2 = default_value);
Example of syntax with two default arguments:
void display(char ch = '*', int n = 10);
Here, if no arguments are passed, ch defaults to '*' and n defaults to 10.
Part 3: Program to Display N Number of Characters Using Default Arguments (4 marks)
#include <iostream>
using namespace std;
// Function declaration with default arguments
// ch = character to print (default: '*')
// n = number of times to print (default: 3)
void printChar(char ch = '*', int n = 3);
int main()
{
cout << "Using both default arguments (no arguments passed):" << endl;
printChar();
// Output: ***
cout << "\nUsing one argument (only character passed):" << endl;
printChar('#');
// Output: ###
cout << "\nUsing both arguments (no defaults used):" << endl;
printChar('@', 7);
// Output: @@@@@@@
cout << "\nUsing character '$' with 5 times:" << endl;
printChar('$', 5);
// Output: $$$$$
return 0;
}
// Function definition
void printChar(char ch, int n)
{
cout << "Character: " << ch << " | Printed " << n << " time(s): ";
for (int i = 1; i <= n; i++)
{
cout << ch;
}
cout << endl;
}
Output:
Using both default arguments (no arguments passed):
Character: * | Printed 3 time(s): ***
Using one argument (only character passed):
Character: # | Printed 3 time(s): ###
Using both arguments (no defaults used):
Character: @ | Printed 7 time(s): @@@@@@@
Using character '$' with 5 times:
Character: $ | Printed 5 time(s): $$$$$
Explanation of the Program:
| Function Call | ch used | n used | Source |
|---|---|---|---|
printChar() | '*' | 3 | Both defaults used |
printChar('#') | '#' | 3 | n default used |
printChar('@', 7) | '@' | 7 | No defaults used |
printChar('$', 5) | '$' | 5 | No defaults used |
Important Note: Default arguments are written in the function declaration/prototype, not in the definition. The compiler substitutes the default value when the argument is omitted in the function call.
2asked 4xavg 9 marks · due (skipped 2080.1) · Types of inheritanceAnswerHideState the use of new operator. An educational institute wishes to maintain a data of its employee. The hierarchical relationships of related classes are as follows. Define all the classes to represent above hierarchy and define functions to retrieve individual information as and when required.[10]
State the use of new operator. An educational institute wishes to maintain a data of its employee. The hierarchical relationships of related classes are as follows. Define all the classes to represent above hierarchy and define functions to retrieve individual information as and when required.[10]
New Operator and Employee Hierarchy in C++
Use of new Operator (2 marks)
The new operator in C++ is used for dynamic memory allocation. It allocates memory at runtime from the heap (free store) and returns a pointer to the beginning of the allocated memory block.
Key uses:
- Allocates memory for a variable or object during program execution
- Returns a pointer to the allocated memory
- Memory persists until explicitly released using
delete - Syntax:
pointer_variable = new data_type;
Example:
int *ptr = new int; // allocates memory for one integer
int *arr = new int[10]; // allocates memory for array of 10 integers
delete ptr; // free single variable
delete[] arr; // free array
Employee Hierarchy Program (8 marks)
Class Hierarchy Structure
Employee
(name, emp_id)
|
________________
| |
Teacher Officer
(subject, (department,
salary) salary)
|
Typist
(speed,
salary)
Complete C++ Program
#include<iostream>
#include<string>
using namespace std;
// ─── Base Class ───────────────────────────────────────────────
class Employee {
protected:
string name;
int emp_id;
public:
// Function to set employee data
void getEmployeeData() {
cout << "Enter Employee Name: ";
cin >> name;
cout << "Enter Employee ID: ";
cin >> emp_id;
}
// Function to display employee data
void showEmployeeData() {
cout << "\n--- Employee Information ---" << endl;
cout << "Name : " << name << endl;
cout << "Emp ID : " << emp_id << endl;
}
};
// ─── Derived Class: Teacher ────────────────────────────────────
class Teacher : public Employee {
protected:
string subject;
float salary;
public:
// Function to set teacher data
void getTeacherData() {
getEmployeeData(); // call base class function
cout << "Enter Subject Specialization: ";
cin >> subject;
cout << "Enter Salary: ";
cin >> salary;
}
// Function to display teacher data
void showTeacherData() {
showEmployeeData(); // call base class function
cout << "Subject : " << subject << endl;
cout << "Salary : " << salary << endl;
}
};
// ─── Derived Class: Typist (derived from Teacher) ─────────────
class Typist : public Teacher {
private:
int typingSpeed; // words per minute
public:
// Function to set typist data
void getTypistData() {
getTeacherData();
cout << "Enter Typing Speed (wpm): ";
cin >> typingSpeed;
}
// Function to display typist data
void showTypistData() {
showTeacherData();
cout << "Typing Speed: " << typingSpeed << " wpm" << endl;
}
};
// ─── Derived Class: Officer ────────────────────────────────────
class Officer : public Employee {
private:
string department;
float salary;
public:
// Function to set officer data
void getOfficerData() {
getEmployeeData(); // call base class function
cout << "Enter Department: ";
cin >> department;
cout << "Enter Salary: ";
cin >> salary;
}
// Function to display officer data
void showOfficerData() {
showEmployeeData(); // call base class function
cout << "Department: " << department << endl;
cout << "Salary : " << salary << endl;
}
};
// ─── Main Function ─────────────────────────────────────────────
int main() {
int choice;
cout << "===== Educational Institute Employee System =====" << endl;
cout << "1. Teacher\n2. Typist\n3. Officer" << endl;
cout << "Enter your choice: ";
cin >> choice;
// Using new operator for dynamic object creation
if (choice == 1) {
Teacher *t = new Teacher;
t->getTeacherData();
t->showTeacherData();
delete t;
}
else if (choice == 2) {
Typist *ty = new Typist;
ty->getTypistData();
ty->showTypistData();
delete ty;
}
else if (choice == 3) {
Officer *o = new Officer;
o->getOfficerData();
o->showOfficerData();
delete o;
}
else {
cout << "Invalid choice!" << endl;
}
return 0;
}
Sample Output
===== Educational Institute Employee System =====
1. Teacher
2. Typist
3. Officer
Enter your choice: 1
Enter Employee Name: Ram
Enter Employee ID: 101
Enter Subject Specialization: Mathematics
Enter Salary: 45000
--- Employee Information ---
Name : Ram
Emp ID : 101
Subject : Mathematics
Salary : 45000
Key Concepts Used
| Concept | Application |
|---|---|
| Base Class | Employee holds common data (name, emp_id) |
| Inheritance | Teacher, Officer inherit from Employee; Typist inherits from Teacher |
protected members | Allow derived classes to access base class data directly |
new operator | Used to create objects dynamically at runtime |
| Function overriding | Each derived class defines its own show and get functions |
public inheritance | Derived class inherits all public and protected members of base class |
**
3asked 4xavg 5 marks · due (skipped 2080.1) · Exceptional HandlingAnswerHideList any two operators that cannot be overloaded. Write a program to handle the possible exception in taking 'age' as input. Here the exception must be thrown in the input is negative or greater than 200. [5]
List any two operators that cannot be overloaded. Write a program to handle the possible exception in taking 'age' as input. Here the exception must be thrown in the input is negative or greater than 200. [5]
Answer
Two Operators That Cannot Be Overloaded
The following operators cannot be overloaded in C++:
| Operator | Name |
|---|---|
:: | Scope Resolution Operator |
?: | Ternary (Conditional) Operator |
Other examples include:
.(member access),.*(pointer to member),sizeof.
Program to Handle Exception for Invalid Age Input
The program throws an exception if the entered age is negative or greater than 200.
#include <iostream>
using namespace std;
// Custom Exception Class for Age
class AgeException {
private:
string message;
public:
AgeException(string msg) {
message = msg;
}
string getMessage() {
return message;
}
};
// Function to validate and return age
int getAge(int age) {
if (age < 0) {
throw AgeException("Invalid age: Age cannot be negative.");
}
else if (age > 200) {
throw AgeException("Invalid age: Age cannot be greater than 200.");
}
return age;
}
int main() {
int age;
cout << "Enter age: ";
cin >> age;
try {
int validAge = getAge(age);
cout << "Valid Age entered: " << validAge << endl;
}
catch (AgeException e) {
cout << "Exception caught: " << e.getMessage() << endl;
}
return 0;
}
Sample Output
Case 1: Valid Input
Enter age: 25
Valid Age entered: 25
Case 2: Negative Age
Enter age: -5
Exception caught: Invalid age: Age cannot be negative.
Case 3: Age Greater Than 200
Enter age: 250
Exception caught: Invalid age: Age cannot be greater than 200.
Explanation
- The
AgeExceptionclass is a user-defined exception class that stores an error message. - The
getAge()function throws anAgeExceptionobject when the age is invalid (negative or > 200). - In
main(), thetryblock callsgetAge()and thecatchblock handles the thrown exception by printing the error message. - This approach separates error-handling code from normal program code, which is one of the key uses of exception handling as stated in the notes.
4asked 3xavg 7 marks · due (skipped 2080.1) · Static membersAnswerHideWrite a C++ program to display the number of objects created using static member. [5]
Write a C++ program to display the number of objects created using static member. [5]
A static data member is shared by all objects of a class. It is initialized only once and retains its value throughout the program. It is used here to count how many objects have been created, because every time a constructor is called (...
5asked 4xavg 9 marks · Initialization of class objectsAnswerHideWhat is destructor? List its characteristics. Explain the use of default copy constructor with an appropriate example.[10]
What is destructor? List its characteristics. Explain the use of default copy constructor with an appropriate example.[10]
Destructor, Its Characteristics, and Default Copy Constructor
1. Destructor (Definition)
A destructor is a special member function of a class that destructs or deletes an object and performs cleanup operations (such as releasing memory) when the object is no longer needed.
When is a Destructor Called?
A destructor is called automatically when:
- The function ends (object goes out of scope of a function)
- The program ends
- A block containing local variables ends
- The
deleteoperator is called on a dynamically allocated object
2. Characteristics of Destructor
| # | Characteristic |
|---|---|
| 1 | The destructor has the same name as the class, preceded by a tilde symbol (~) |
| 2 | Destructors do not take any arguments (cannot be overloaded) |
| 3 | Destructors do not return any value (not even void) |
| 4 | There can be only one destructor in a class |
| 5 | It is called automatically when the object goes out of scope or is deleted |
| 6 | It is typically used to free dynamically allocated memory and release resources |
| 7 | It should be declared in the public section of the class |
3. Example of Destructor
#include <iostream>
#include <string.h>
using namespace std;
class String {
private:
char *s;
int size;
public:
String(char *c) { // Constructor
size = strlen(c);
s = new char[size + 1];
strcpy(s, c);
cout << "Constructor called. String: " << s << endl;
}
~String() { // Destructor
delete[] s; // Free dynamically allocated memory
cout << "Destructor called. Memory freed." << endl;
}
};
int main() {
String str("Hello"); // Constructor is called here
// Destructor is called automatically when str goes out of scope
return 0;
}
Output:
Constructor called. String: Hello
Destructor called. Memory freed.
4. Default Copy Constructor
Definition
A copy constructor is a special constructor that creates a new object as a copy of an existing object of the same class. When the programmer does not define a copy constructor explicitly, C++ automatically provides a default copy constructor.
The default copy constructor performs a member-wise (shallow) copy of all data members from one object to another.
Syntax
ClassName (const ClassName &old_object);
How the Default Copy Constructor Works
- It copies each data member of the source object directly into the corresponding data member of the new object.
- This is called a shallow copy because it copies values as-is, including pointer addresses (not the data pointed to).
When is the Copy Constructor Invoked?
- When an object is initialized with another object of the same class
- When an object is passed by value to a function
- When an object is returned by value from a function
5. Example: Default Copy Constructor
#include <iostream>
using namespace std;
class Student {
private:
int rollNo;
float marks;
public:
// Parameterized Constructor
Student(int r, float m) {
rollNo = r;
marks = m;
}
void display() {
cout << "Roll No: " << rollNo
<< ", Marks: " << marks << endl;
}
};
int main() {
Student s1(101, 85.5); // Original object created using constructor
Student s2 = s1; // Default copy constructor is called here
// s2 is a copy of s1
cout << "Object s1 -> ";
s1.display();
cout << "Object s2 -> ";
s2.display();
return 0;
}
Output:
Object s1 -> Roll No: 101, Marks: 85.5
Object s2 -> Roll No: 101, Marks: 85.5
Explanation
| Step | What Happens |
|---|---|
Student s1(101, 85.5) | Parameterized constructor is called; s1.rollNo = 101, s1.marks = 85.5 |
Student s2 = s1 | Default copy constructor is invoked; copies rollNo and marks from s1 to s2 |
Both s1 and s2 display the same values | Member-wise copy was successful |
6. Limitation of Default Copy Constructor (Shallow Copy Problem)
When a class contains pointer members, the default copy constructor copies only the address of the pointer, not the actual data. This means both objects point to the same memory location, which can cause problems (double deletion, data corruption). In such cases, a user-defined copy constructor performing a deep copy is required.
s1.ptr -----> [Memory Block]
s2.ptr -----> [Same Memory Block] <-- Problem!
Summary Table
| Feature | Destructor | Default Copy Constructor |
|---|---|---|
| Purpose | Cleans up / frees resources | Creates a copy of an object |
| Symbol | ~ClassName() | ClassName(const ClassName &obj) |
| Arguments | None | Reference to same class object |
| Return type | None | None |
| Count per class | Only one | Only one (default) |
| Called automatically | Yes, on scope exit | Yes, on object copy/pass by value |
Most repeated questions
Topics asked at least twice, most-asked first.
asked 6xavg 6 marks · 2080, 2079, 2078, 2076, 2075AnswerHideWhen inline functions may not work? Define and write syntax for default arguments. Write a program to display N number of characters by using default arguments for both parameters. Assume that the function takes two arguments, one character to be printed and other how many times the character to be printed respectively.[10]
When inline functions may not work? Define and write syntax for default arguments. Write a program to display N number of characters by using default arguments for both parameters. Assume that the function takes two arguments, one character to be printed and other how many times the character to be printed respectively.[10]
Answer: Inline Functions, Default Arguments, and Program
Part 1: When Inline Functions May NOT Work (3 marks)
The compiler may ignore the inline request and treat the function as a normal function in the following situations:
-
Function contains loops - If the inline function contains looping statements such as
for,while, ordo-while, the compiler will not inline it. -
Function contains static variables - If the function has static local variables declared inside it, it cannot be inlined.
-
Function is recursive - A recursive inline function (a function that calls itself) cannot be expanded inline.
-
Function contains switch or goto statements - Functions containing
switchorgotocontrol statements may not be inlined. -
Function is too large/complex - If the function body is too large, inlining it would increase code size significantly, so the compiler refuses to inline it.
-
Function returns a value and contains multiple return statements - In some cases, multiple return points prevent inlining.
Note: The
inlinekeyword is only a request to the compiler, not a command. The compiler has the final decision.
Part 2: Default Arguments - Definition and Syntax (3 marks)
Definition:
A default argument is a value provided in a function declaration that is automatically assigned by the compiler if the calling function does not provide a value for that argument. It allows a function to be called with fewer arguments than it is defined to accept.
Key Rules:
- Default arguments must be specified from right to left (trailing arguments first).
- Once a default value is assigned to a parameter, all parameters to its right must also have default values.
- Default values are specified in the function declaration (prototype).
Syntax:
return_type function_name(datatype param1, datatype param2 = default_value);
Example of syntax with two default arguments:
void display(char ch = '*', int n = 10);
Here, if no arguments are passed, ch defaults to '*' and n defaults to 10.
Part 3: Program to Display N Number of Characters Using Default Arguments (4 marks)
#include <iostream>
using namespace std;
// Function declaration with default arguments
// ch = character to print (default: '*')
// n = number of times to print (default: 3)
void printChar(char ch = '*', int n = 3);
int main()
{
cout << "Using both default arguments (no arguments passed):" << endl;
printChar();
// Output: ***
cout << "\nUsing one argument (only character passed):" << endl;
printChar('#');
// Output: ###
cout << "\nUsing both arguments (no defaults used):" << endl;
printChar('@', 7);
// Output: @@@@@@@
cout << "\nUsing character '$' with 5 times:" << endl;
printChar('$', 5);
// Output: $$$$$
return 0;
}
// Function definition
void printChar(char ch, int n)
{
cout << "Character: " << ch << " | Printed " << n << " time(s): ";
for (int i = 1; i <= n; i++)
{
cout << ch;
}
cout << endl;
}
Output:
Using both default arguments (no arguments passed):
Character: * | Printed 3 time(s): ***
Using one argument (only character passed):
Character: # | Printed 3 time(s): ###
Using both arguments (no defaults used):
Character: @ | Printed 7 time(s): @@@@@@@
Using character '$' with 5 times:
Character: $ | Printed 5 time(s): $$$$$
Explanation of the Program:
| Function Call | ch used | n used | Source |
|---|---|---|---|
printChar() | '*' | 3 | Both defaults used |
printChar('#') | '#' | 3 | n default used |
printChar('@', 7) | '@' | 7 | No defaults used |
printChar('$', 5) | '$' | 5 | No defaults used |
Important Note: Default arguments are written in the function declaration/prototype, not in the definition. The compiler substitutes the default value when the argument is omitted in the function call.
asked 4xavg 9 marks · 2080, 2078, 2076, 2075AnswerHideState the use of new operator. An educational institute wishes to maintain a data of its employee. The hierarchical relationships of related classes are as follows. Define all the classes to represent above hierarchy and define functions to retrieve individual information as and when required.[10]
State the use of new operator. An educational institute wishes to maintain a data of its employee. The hierarchical relationships of related classes are as follows. Define all the classes to represent above hierarchy and define functions to retrieve individual information as and when required.[10]
New Operator and Employee Hierarchy in C++
Use of new Operator (2 marks)
The new operator in C++ is used for dynamic memory allocation. It allocates memory at runtime from the heap (free store) and returns a pointer to the beginning of the allocated memory block.
Key uses:
- Allocates memory for a variable or object during program execution
- Returns a pointer to the allocated memory
- Memory persists until explicitly released using
delete - Syntax:
pointer_variable = new data_type;
Example:
int *ptr = new int; // allocates memory for one integer
int *arr = new int[10]; // allocates memory for array of 10 integers
delete ptr; // free single variable
delete[] arr; // free array
Employee Hierarchy Program (8 marks)
Class Hierarchy Structure
Employee
(name, emp_id)
|
________________
| |
Teacher Officer
(subject, (department,
salary) salary)
|
Typist
(speed,
salary)
Complete C++ Program
#include<iostream>
#include<string>
using namespace std;
// ─── Base Class ───────────────────────────────────────────────
class Employee {
protected:
string name;
int emp_id;
public:
// Function to set employee data
void getEmployeeData() {
cout << "Enter Employee Name: ";
cin >> name;
cout << "Enter Employee ID: ";
cin >> emp_id;
}
// Function to display employee data
void showEmployeeData() {
cout << "\n--- Employee Information ---" << endl;
cout << "Name : " << name << endl;
cout << "Emp ID : " << emp_id << endl;
}
};
// ─── Derived Class: Teacher ────────────────────────────────────
class Teacher : public Employee {
protected:
string subject;
float salary;
public:
// Function to set teacher data
void getTeacherData() {
getEmployeeData(); // call base class function
cout << "Enter Subject Specialization: ";
cin >> subject;
cout << "Enter Salary: ";
cin >> salary;
}
// Function to display teacher data
void showTeacherData() {
showEmployeeData(); // call base class function
cout << "Subject : " << subject << endl;
cout << "Salary : " << salary << endl;
}
};
// ─── Derived Class: Typist (derived from Teacher) ─────────────
class Typist : public Teacher {
private:
int typingSpeed; // words per minute
public:
// Function to set typist data
void getTypistData() {
getTeacherData();
cout << "Enter Typing Speed (wpm): ";
cin >> typingSpeed;
}
// Function to display typist data
void showTypistData() {
showTeacherData();
cout << "Typing Speed: " << typingSpeed << " wpm" << endl;
}
};
// ─── Derived Class: Officer ────────────────────────────────────
class Officer : public Employee {
private:
string department;
float salary;
public:
// Function to set officer data
void getOfficerData() {
getEmployeeData(); // call base class function
cout << "Enter Department: ";
cin >> department;
cout << "Enter Salary: ";
cin >> salary;
}
// Function to display officer data
void showOfficerData() {
showEmployeeData(); // call base class function
cout << "Department: " << department << endl;
cout << "Salary : " << salary << endl;
}
};
// ─── Main Function ─────────────────────────────────────────────
int main() {
int choice;
cout << "===== Educational Institute Employee System =====" << endl;
cout << "1. Teacher\n2. Typist\n3. Officer" << endl;
cout << "Enter your choice: ";
cin >> choice;
// Using new operator for dynamic object creation
if (choice == 1) {
Teacher *t = new Teacher;
t->getTeacherData();
t->showTeacherData();
delete t;
}
else if (choice == 2) {
Typist *ty = new Typist;
ty->getTypistData();
ty->showTypistData();
delete ty;
}
else if (choice == 3) {
Officer *o = new Officer;
o->getOfficerData();
o->showOfficerData();
delete o;
}
else {
cout << "Invalid choice!" << endl;
}
return 0;
}
Sample Output
===== Educational Institute Employee System =====
1. Teacher
2. Typist
3. Officer
Enter your choice: 1
Enter Employee Name: Ram
Enter Employee ID: 101
Enter Subject Specialization: Mathematics
Enter Salary: 45000
--- Employee Information ---
Name : Ram
Emp ID : 101
Subject : Mathematics
Salary : 45000
Key Concepts Used
| Concept | Application |
|---|---|
| Base Class | Employee holds common data (name, emp_id) |
| Inheritance | Teacher, Officer inherit from Employee; Typist inherits from Teacher |
protected members | Allow derived classes to access base class data directly |
new operator | Used to create objects dynamically at runtime |
| Function overriding | Each derived class defines its own show and get functions |
public inheritance | Derived class inherits all public and protected members of base class |
**
asked 4xavg 5 marks · 2080, 2078, 2076, 2075AnswerHideList any two operators that cannot be overloaded. Write a program to handle the possible exception in taking 'age' as input. Here the exception must be thrown in the input is negative or greater than 200. [5]
List any two operators that cannot be overloaded. Write a program to handle the possible exception in taking 'age' as input. Here the exception must be thrown in the input is negative or greater than 200. [5]
Answer
Two Operators That Cannot Be Overloaded
The following operators cannot be overloaded in C++:
| Operator | Name |
|---|---|
:: | Scope Resolution Operator |
?: | Ternary (Conditional) Operator |
Other examples include:
.(member access),.*(pointer to member),sizeof.
Program to Handle Exception for Invalid Age Input
The program throws an exception if the entered age is negative or greater than 200.
#include <iostream>
using namespace std;
// Custom Exception Class for Age
class AgeException {
private:
string message;
public:
AgeException(string msg) {
message = msg;
}
string getMessage() {
return message;
}
};
// Function to validate and return age
int getAge(int age) {
if (age < 0) {
throw AgeException("Invalid age: Age cannot be negative.");
}
else if (age > 200) {
throw AgeException("Invalid age: Age cannot be greater than 200.");
}
return age;
}
int main() {
int age;
cout << "Enter age: ";
cin >> age;
try {
int validAge = getAge(age);
cout << "Valid Age entered: " << validAge << endl;
}
catch (AgeException e) {
cout << "Exception caught: " << e.getMessage() << endl;
}
return 0;
}
Sample Output
Case 1: Valid Input
Enter age: 25
Valid Age entered: 25
Case 2: Negative Age
Enter age: -5
Exception caught: Invalid age: Age cannot be negative.
Case 3: Age Greater Than 200
Enter age: 250
Exception caught: Invalid age: Age cannot be greater than 200.
Explanation
- The
AgeExceptionclass is a user-defined exception class that stores an error message. - The
getAge()function throws anAgeExceptionobject when the age is invalid (negative or > 200). - In
main(), thetryblock callsgetAge()and thecatchblock handles the thrown exception by printing the error message. - This approach separates error-handling code from normal program code, which is one of the key uses of exception handling as stated in the notes.
asked 4xavg 9 marks · 2080.1, 2080, 2079, 2076AnswerHideWhat is destructor? List its characteristics. Explain the use of default copy constructor with an appropriate example.[10]
What is destructor? List its characteristics. Explain the use of default copy constructor with an appropriate example.[10]
Destructor, Its Characteristics, and Default Copy Constructor
1. Destructor (Definition)
A destructor is a special member function of a class that destructs or deletes an object and performs cleanup operations (such as releasing memory) when the object is no longer needed.
When is a Destructor Called?
A destructor is called automatically when:
- The function ends (object goes out of scope of a function)
- The program ends
- A block containing local variables ends
- The
deleteoperator is called on a dynamically allocated object
2. Characteristics of Destructor
| # | Characteristic |
|---|---|
| 1 | The destructor has the same name as the class, preceded by a tilde symbol (~) |
| 2 | Destructors do not take any arguments (cannot be overloaded) |
| 3 | Destructors do not return any value (not even void) |
| 4 | There can be only one destructor in a class |
| 5 | It is called automatically when the object goes out of scope or is deleted |
| 6 | It is typically used to free dynamically allocated memory and release resources |
| 7 | It should be declared in the public section of the class |
3. Example of Destructor
#include <iostream>
#include <string.h>
using namespace std;
class String {
private:
char *s;
int size;
public:
String(char *c) { // Constructor
size = strlen(c);
s = new char[size + 1];
strcpy(s, c);
cout << "Constructor called. String: " << s << endl;
}
~String() { // Destructor
delete[] s; // Free dynamically allocated memory
cout << "Destructor called. Memory freed." << endl;
}
};
int main() {
String str("Hello"); // Constructor is called here
// Destructor is called automatically when str goes out of scope
return 0;
}
Output:
Constructor called. String: Hello
Destructor called. Memory freed.
4. Default Copy Constructor
Definition
A copy constructor is a special constructor that creates a new object as a copy of an existing object of the same class. When the programmer does not define a copy constructor explicitly, C++ automatically provides a default copy constructor.
The default copy constructor performs a member-wise (shallow) copy of all data members from one object to another.
Syntax
ClassName (const ClassName &old_object);
How the Default Copy Constructor Works
- It copies each data member of the source object directly into the corresponding data member of the new object.
- This is called a shallow copy because it copies values as-is, including pointer addresses (not the data pointed to).
When is the Copy Constructor Invoked?
- When an object is initialized with another object of the same class
- When an object is passed by value to a function
- When an object is returned by value from a function
5. Example: Default Copy Constructor
#include <iostream>
using namespace std;
class Student {
private:
int rollNo;
float marks;
public:
// Parameterized Constructor
Student(int r, float m) {
rollNo = r;
marks = m;
}
void display() {
cout << "Roll No: " << rollNo
<< ", Marks: " << marks << endl;
}
};
int main() {
Student s1(101, 85.5); // Original object created using constructor
Student s2 = s1; // Default copy constructor is called here
// s2 is a copy of s1
cout << "Object s1 -> ";
s1.display();
cout << "Object s2 -> ";
s2.display();
return 0;
}
Output:
Object s1 -> Roll No: 101, Marks: 85.5
Object s2 -> Roll No: 101, Marks: 85.5
Explanation
| Step | What Happens |
|---|---|
Student s1(101, 85.5) | Parameterized constructor is called; s1.rollNo = 101, s1.marks = 85.5 |
Student s2 = s1 | Default copy constructor is invoked; copies rollNo and marks from s1 to s2 |
Both s1 and s2 display the same values | Member-wise copy was successful |
6. Limitation of Default Copy Constructor (Shallow Copy Problem)
When a class contains pointer members, the default copy constructor copies only the address of the pointer, not the actual data. This means both objects point to the same memory location, which can cause problems (double deletion, data corruption). In such cases, a user-defined copy constructor performing a deep copy is required.
s1.ptr -----> [Memory Block]
s2.ptr -----> [Same Memory Block] <-- Problem!
Summary Table
| Feature | Destructor | Default Copy Constructor |
|---|---|---|
| Purpose | Cleans up / frees resources | Creates a copy of an object |
| Symbol | ~ClassName() | ClassName(const ClassName &obj) |
| Arguments | None | Reference to same class object |
| Return type | None | None |
| Count per class | Only one | Only one (default) |
| Called automatically | Yes, on scope exit | Yes, on object copy/pass by value |
asked 4xavg 8 marks · 2080.1, 2079, 2078, 2075AnswerHideCreate two classes Rupee and Dollar respectively. Write conversion operator to convert between Rupee and Dollar assuming that 1 dollar equals 133 rupees. Write a main program that allows the user to enter an amount in either currency and then converts it to other currency and displays the result. [5]
Create two classes Rupee and Dollar respectively. Write conversion operator to convert between Rupee and Dollar assuming that 1 dollar equals 133 rupees. Write a main program that allows the user to enter an amount in either currency and then converts it to other currency and displays the result. [5]
This problem uses type conversion between class objects using a conversion operator (casting operator) defined inside the source class. The conversion operator converts an object of one class type to another class type. Rate: 1 Dollar = ...
asked 3xavg 7 marks · 2080, 2078, 2075AnswerHideWrite a C++ program to display the number of objects created using static member. [5]
Write a C++ program to display the number of objects created using static member. [5]
A static data member is shared by all objects of a class. It is initialized only once and retains its value throughout the program. It is used here to count how many objects have been created, because every time a constructor is called (...
asked 3xavg 5 marks · 2080, 2079, 2078AnswerHideExplain about friend function and friend class with an example. [5]
Explain about friend function and friend class with an example. [5]
A friend function is a function that is not a member of a class but has access to the private and protected members of that class. - The declaration is placed inside the class body (in either private or public section) preceded by the ke...
asked 3xavg 5 marks · 2080.1, 2076, 2075AnswerHideExplain function template overloading with suitable example. [5]
Explain function template overloading with suitable example. [5]
Function template overloading means defining more than one template function with the same name but with different numbers of parameters or different logic, so that the compiler selects the appropriate version based on the arguments pass...
asked 2xavg 10 marks · 2079, 2076AnswerHideWhat is operator overloading? Why it is necessary to overload and operator? Write a program for overloading comparison operators.[10]
What is operator overloading? Why it is necessary to overload and operator? Write a program for overloading comparison operators.[10]
"The method of making operators to work for user defined class and having the ability to provide operators with a special user defined meaning is known as operator overloading." In simple terms, operator overloading allows us to redefine...
asked 2xavg 8 marks · 2080, 2075AnswerHideWhat do you mean by stream? Explain different stream class for file input/output. [5]
What do you mean by stream? Explain different stream class for file input/output. [5]
Stream and Stream Classes for File I/O in C++
What is a Stream?
A stream is a sequence of bytes flowing between a program and an input/output device (such as a file, keyboard, or screen). It acts as an abstraction layer between the program and the actual device.
- We have been using the
iostreamstandard library, which providescinandcoutfor reading from standard input and writing to standard output respectively. - For file-based I/O, C++ provides another standard library called
fstream, which defines specialized stream classes to read from and write to files.
To perform file processing in C++, the header file
<fstream>must be included in the source file.
Stream Classes for File Input/Output
The fstream library defines three main data types (stream classes):
1. ifstream (Input File Stream)
- Represents the input file stream.
- Used to read information from files.
- Derived from
istream.
Example:
#include <fstream>
using namespace std;
int main() {
ifstream fin;
fin.open("data.txt"); // open file for reading
char ch;
while (fin >> ch)
cout << ch;
fin.close();
return 0;
}
2. ofstream (Output File Stream)
- Represents the output file stream.
- Used to create files and write information to files.
- Derived from
ostream.
Example:
#include <fstream>
using namespace std;
int main() {
ofstream fout;
fout.open("data.txt"); // open file for writing
fout << "Hello, File!";
fout.close();
return 0;
}
3. fstream (File Stream)
- Represents the general file stream.
- Has the capabilities of both
ifstreamandofstream. - Can create files, write information to files, and read information from files.
Example:
#include <fstream>
using namespace std;
int main() {
fstream file;
file.open("data.txt", ios::in | ios::out); // read and write
file << "Writing data";
file.close();
return 0;
}
Summary Table
| Class | Purpose | Operation |
|---|---|---|
ifstream | Input file stream | Read from files |
ofstream | Output file stream | Create and write to files |
fstream | General file stream | Read and write to files |
File Pointer Manipulation Functions
The stream classes also support functions to manage file pointer positions:
| Function | Description |
|---|---|
seekg() | Moves the get (input) pointer to a specified location |
seekp() | Moves the put (output) pointer to a specified location |
tellg() | Returns the current position of the get pointer |
tellp() | Returns the current position of the put pointer |
These functions allow random access within a file, enabling reading or writing at any desired position.
asked 2xavg 5 marks · 2080AnswerHideWhat is the use of reinterpret cast operator? Why do we need virtual function? [5]
What is the use of reinterpret cast operator? Why do we need virtual function? [5]
Reinterpret Cast Operator and Virtual Functions
Part 1: reinterpret_cast Operator
Definition
reinterpret_cast is a cast operator in C++ that converts one pointer type to another pointer type, even if the types are unrelated. It forces the compiler to treat the bit pattern of one type as if it were another type entirely.
As noted in the reference: "A cast operator is a special operator that forces one data type to be converted into another."
Syntax
reinterpret_cast<new_type>(expression);
Uses of reinterpret_cast
| Use Case | Description |
|---|---|
| Pointer to pointer conversion | Convert int* to char* or any unrelated pointer type |
| Pointer to integer conversion | Store a pointer value as an integer |
| Integer to pointer conversion | Convert an integer back to a pointer |
| Low-level memory manipulation | Used in hardware/system programming |
Example
#include <iostream>
using namespace std;
int main() {
int a = 65;
int* ptr = &a;
// Reinterpret int pointer as char pointer
char* cptr = reinterpret_cast<char*>(ptr);
cout << "Integer value: " << *ptr << endl;
cout << "Char interpretation: " << *cptr << endl; // Output: A
return 0;
}
Key Points
- It does not check type safety; the programmer is responsible for correctness.
- It is the most dangerous cast and should be used with caution.
- Commonly used in low-level programming, such as device drivers or memory-mapped I/O.
Part 2: Why Do We Need Virtual Functions?
Problem Without Virtual Functions
When a base class pointer points to a derived class object, calling an overridden function without virtual will always call the base class version due to static (early) binding.
From the reference: "When a member function is not virtual, the function called is determined only by the type of the expression to the left of dot (.) or arrow (->) operator. This is called the static type."
What is a Virtual Function?
A virtual function is a member function declared in the base class using the keyword virtual, which tells the compiler to perform late binding (runtime binding) so that the correct overridden function is called based on the actual object type, not the pointer type.
From the reference: "Late Binding is achieved using Virtual functions."
Example Demonstrating the Need
#include <iostream>
using namespace std;
class Base {
public:
virtual void print() { // virtual function
cout << "Print Base class" << endl;
}
void show() { // non-virtual function
cout << "Show Base class" << endl;
}
};
class Derived : public Base {
public:
void print() {
cout << "Print Derived class" << endl;
}
void show() {
cout << "Show Derived class" << endl;
}
};
int main() {
Base* bptr;
Derived d;
bptr = &d;
bptr->print(); // Virtual -> calls Derived version (runtime binding)
bptr->show(); // Non-virtual -> calls Base version (compile-time binding)
return 0;
}
Output
Print Derived class
Show Base class
Why We Need Virtual Functions
- Runtime Polymorphism: Enables the correct function to be called based on the actual object at runtime, not the pointer type.
- Flexibility: A single base class pointer can manage objects of multiple derived classes and call appropriate methods.
- Extensibility: New derived classes can be added without changing existing code.
- Correct Overriding Behavior: Without
virtual, overriding does not work as expected through base class pointers.
Important Note
From the reference: "If we have created a virtual function in the base class and it is being overridden in the derived class, then we don't need the virtual keyword in the derived class -- functions are automatically considered as virtual functions in the derived class."
Summary Table
| Feature | reinterpret_cast | Virtual Function |
|---|---|---|
| Purpose | Low-level type conversion | Runtime polymorphism |
| Binding | N/A | Late (runtime) binding |
| Safety | Unsafe, programmer's responsibility | Safe, resolved by vtable |
asked 2xavg 5 marks · 2079, 2076AnswerHideDescribe the characteristics of object oriented programming languages. [5]
Describe the characteristics of object oriented programming languages. [5]
Object-Oriented Programming (OOP) is a programming paradigm that organizes software design around objects rather than functions and logic. The key characteristics (terms) of OOP are described below: --- - Objects are the basic run-time e...
asked 2xavg 5 marks · 2079, 2076AnswerHideHow dynamic memory allocation is done using new and delete? Write program for illustrating use of new and delete. [5]
How dynamic memory allocation is done using new and delete? Write program for illustrating use of new and delete. [5]
The process of allocating memory during runtime (execution time) of a program using the heap space of memory, to reduce wastage of memory, is called dynamic memory allocation. - new - memory allocation operator (allocates memory at runti...
asked 2xavg 5 marks · 2078, 2075AnswerHideWhat is the use of get and getline functions? Explain with suitable example. [5]
What is the use of get and getline functions? Explain with suitable example. [5]
Both get() and getline() are input functions in C++ used to read character(s) or strings from the input stream (cin). They are particularly useful when reading input that includes whitespace characters (spaces, tabs, newlines), which the...
asked 2xavg 5 marks · 2078, 2076AnswerHideWrite short notes on: a. Manipulators b. Protected Access Specifier [5]
Write short notes on: a. Manipulators b. Protected Access Specifier [5]
--- Manipulators are special functions used in C++ to format the output or manipulate the stream in a convenient way. They are used along with the insertion (<<) and extraction () operators. In the context of file access, each file has t...
Study every one of these with model answers, flashcards, and MCQs.
Open CSC166 study modes