Polymorphism is one of the core concepts of Object-Oriented Programming (OOP) in C++. It allows one function or method to behave differently based on the context. The word "polymorphism" comes from Greek, meaning "many forms." In C++, polymorphism allows you to use a single interface to represent different types of objects.
There are two types of polymorphism in C++:
Compile-time polymorphism is resolved during the compilation process. It allows you to perform method overloading and operator overloading. This type of polymorphism is achieved by function overloading or operator overloading.
Function overloading is when multiple functions have the same name but different parameters (number or type of parameters). The appropriate function is called based on the function signature.
class Example { public: void display(int i) { cout << "Integer: " << i << endl; } void display(double d) { cout << "Double: " << d << endl; } }; int main() { Example obj; obj.display(5); // Calls display(int) obj.display(5.5); // Calls display(double) return 0; }
In this example, we have two functions with the same name display() but with different parameters. The compiler chooses the appropriate function based on the argument type.
Operator overloading allows you to redefine the meaning of operators for user-defined classes. For example, you can overload the +
operator to add two objects of a custom class.
class Complex { private: int real, imag; public: Complex(int r, int i) : real(r), imag(i) {} Complex operator + (const Complex& obj) { return Complex(real + obj.real, imag + obj.imag); } void display() { cout << real << " + " << imag << "i" << endl; } }; int main() { Complex num1(3, 4), num2(1, 2); Complex result = num1 + num2; // Using overloaded + operator result.display(); return 0; }
In this example, the +
operator is overloaded to add two Complex numbers. The operator is now defined for user-defined types, allowing objects of the class to use the + operator.
Runtime polymorphism is achieved through inheritance and virtual functions. It occurs at runtime, and the function that gets called is determined dynamically. The key to runtime polymorphism in C++ is the use of virtual functions and base class pointers or references to derived class objects.
A virtual function is a member function in the base class that you expect to be overridden in derived classes. By declaring a function as virtual in the base class, you ensure that the correct function is called for an object, regardless of the type of reference (base or derived) used for the function call.
class Animal { public: virtual void sound() { cout << "Animal makes a sound" << endl; } }; class Dog : public Animal { public: void sound() override { cout << "Dog barks" << endl; } }; class Cat : public Animal { public: void sound() override { cout << "Cat meows" << endl; } }; int main() { Animal* animal; Dog dog; Cat cat; animal = &dog; animal->sound(); // Calls Dog's sound() animal = &cat; animal->sound(); // Calls Cat's sound() return 0; }
In this example, sound() is a virtual function in the base class Animal. When a base class pointer (animal) points to a derived class object (dog or cat), the appropriate overridden version of sound() is called based on the actual object type, not the pointer type.
A virtual destructor is necessary when a class is intended to be used as a base class for other classes. It ensures that the destructors of derived classes are called properly when an object is deleted through a base class pointer.
class Base { public: virtual ~Base() { cout << "Base Destructor" << endl; } }; class Derived : public Base { public: ~Derived() { cout << "Derived Destructor" << endl; } }; int main() { Base* ptr = new Derived(); delete ptr; // Calls Derived destructor, then Base destructor return 0; }
Here, the destructor of the derived class Derived is called first, and then the base class Base destructor is called, thanks to the virtual destructor.
Type of Polymorphism | Description | Example |
---|---|---|
Compile-time Polymorphism | Determined at compile time; includes function overloading and operator overloading. | Function overloading and operator overloading examples provided above. |
Runtime Polymorphism | Determined at runtime; achieved using virtual functions and inheritance. | Virtual functions example provided above. |
Polymorphism is a powerful feature in C++ that enables flexibility and reusability. By using both compile-time and runtime polymorphism, you can create programs that are easy to extend and maintain, while keeping the codebase clean and efficient. Understanding how to apply polymorphism in different contexts is essential for mastering object-oriented programming in C++.
Polymorphism is one of the core concepts of Object-Oriented Programming (OOP) in C++. It allows one function or method to behave differently based on the context. The word "polymorphism" comes from Greek, meaning "many forms." In C++, polymorphism allows you to use a single interface to represent different types of objects.
There are two types of polymorphism in C++:
Compile-time polymorphism is resolved during the compilation process. It allows you to perform method overloading and operator overloading. This type of polymorphism is achieved by function overloading or operator overloading.
Function overloading is when multiple functions have the same name but different parameters (number or type of parameters). The appropriate function is called based on the function signature.
class Example { public: void display(int i) { cout << "Integer: " << i << endl; } void display(double d) { cout << "Double: " << d << endl; } }; int main() { Example obj; obj.display(5); // Calls display(int) obj.display(5.5); // Calls display(double) return 0; }
In this example, we have two functions with the same name display() but with different parameters. The compiler chooses the appropriate function based on the argument type.
Operator overloading allows you to redefine the meaning of operators for user-defined classes. For example, you can overload the
+
operator to add two objects of a custom class.
class Complex { private: int real, imag; public: Complex(int r, int i) : real(r), imag(i) {} Complex operator + (const Complex& obj) { return Complex(real + obj.real, imag + obj.imag); } void display() { cout << real << " + " << imag << "i" << endl; } }; int main() { Complex num1(3, 4), num2(1, 2); Complex result = num1 + num2; // Using overloaded + operator result.display(); return 0; }
In this example, the
+
operator is overloaded to add two Complex numbers. The operator is now defined for user-defined types, allowing objects of the class to use the + operator.
Runtime polymorphism is achieved through inheritance and virtual functions. It occurs at runtime, and the function that gets called is determined dynamically. The key to runtime polymorphism in C++ is the use of virtual functions and base class pointers or references to derived class objects.
A virtual function is a member function in the base class that you expect to be overridden in derived classes. By declaring a function as virtual in the base class, you ensure that the correct function is called for an object, regardless of the type of reference (base or derived) used for the function call.
class Animal { public: virtual void sound() { cout << "Animal makes a sound" << endl; } }; class Dog : public Animal { public: void sound() override { cout << "Dog barks" << endl; } }; class Cat : public Animal { public: void sound() override { cout << "Cat meows" << endl; } }; int main() { Animal* animal; Dog dog; Cat cat; animal = &dog; animal->sound(); // Calls Dog's sound() animal = &cat; animal->sound(); // Calls Cat's sound() return 0; }
In this example, sound() is a virtual function in the base class Animal. When a base class pointer (animal) points to a derived class object (dog or cat), the appropriate overridden version of sound() is called based on the actual object type, not the pointer type.
A virtual destructor is necessary when a class is intended to be used as a base class for other classes. It ensures that the destructors of derived classes are called properly when an object is deleted through a base class pointer.
class Base { public: virtual ~Base() { cout << "Base Destructor" << endl; } }; class Derived : public Base { public: ~Derived() { cout << "Derived Destructor" << endl; } }; int main() { Base* ptr = new Derived(); delete ptr; // Calls Derived destructor, then Base destructor return 0; }
Here, the destructor of the derived class Derived is called first, and then the base class Base destructor is called, thanks to the virtual destructor.
Type of Polymorphism | Description | Example |
---|---|---|
Compile-time Polymorphism | Determined at compile time; includes function overloading and operator overloading. | Function overloading and operator overloading examples provided above. |
Runtime Polymorphism | Determined at runtime; achieved using virtual functions and inheritance. | Virtual functions example provided above. |
Polymorphism is a powerful feature in C++ that enables flexibility and reusability. By using both compile-time and runtime polymorphism, you can create programs that are easy to extend and maintain, while keeping the codebase clean and efficient. Understanding how to apply polymorphism in different contexts is essential for mastering object-oriented programming in C++.
A void pointer is a special type of pointer that can point to any data type, making it versatile for generic data handling.
Dynamic memory allocation in C++ refers to allocating memory at runtime using operators like new and delete, providing flexibility in memory management.
Templates in C++ allow functions and classes to operate with generic types, enabling code reusability and type safety.
Iterators are objects that allow traversal through the elements of a container in the STL, providing a uniform way to access elements.
C++ is an object-oriented programming language that extends C by adding features like classes, inheritance, and polymorphism. Unlike C, which is procedural, C++ supports both procedural and object-oriented paradigms.
An array in C++ is declared by specifying the type of its elements followed by the array name and size in square brackets, e.g., int arr[10];.
The new operator allocates memory dynamically on the heap, while the delete operator deallocates memory, preventing memory leaks.
Type casting in C++ is the process of converting a variable from one data type to another, either implicitly or explicitly.
Inheritance is a feature in C++ where a new class (derived class) acquires properties and behaviors (methods) from an existing class (base class).
Operator overloading enables the redefinition of the way operators work for user-defined types, allowing operators to be used with objects of those types.
Function overloading allows multiple functions with the same name but different parameters to coexist in a C++ program, enabling more intuitive function calls.
In C++, a class is declared using the class keyword, followed by the class name and a pair of curly braces containing member variables and functions.
No, a C++ program cannot execute without a main() function, as it is the designated entry point for program execution.
Vectors are dynamic arrays provided by the STL in C++ that can grow or shrink in size during program execution.
A namespace in C++ is a declarative region that provides a scope to the identifiers (names of types, functions, variables) to avoid name conflicts.
The primary difference is that members of a struct are public by default, whereas members of a class are private by default.
The const keyword in C++ is used to define constants, indicating that the value of a variable cannot be changed after initialization.
Exception handling in C++ is a mechanism to handle runtime errors using try, catch, and throw blocks, allowing a program to continue execution after an error.
The STL is a collection of template classes and functions in C++ that provide general-purpose algorithms and data structures like vectors, lists, and maps.
A reference in C++ is an alias for another variable, whereas a pointer holds the memory address of a variable. References cannot be null and must be initialized upon declaration.
Pointers in C++ are variables that store memory addresses of other variables. They allow for dynamic memory allocation and efficient array handling.
Polymorphism allows objects of different classes to be treated as objects of a common base class, enabling a single function or operator to work in different ways.
Constructors are special member functions that initialize objects when they are created. Destructors are called when objects are destroyed, used to release resources.
These access specifiers define the accessibility of class members. Public members are accessible from outside the class, private members are not, and protected members are accessible within the class and by derived classes.
The main() function serves as the entry point for a C++ program. It is where the execution starts and ends.
Copyrights © 2024 letsupdateskills All rights reserved