› Module 5: Object-Oriented Programming › 5.3 Encapsulation
M O D U L E

Module 5: Object-Oriented Programming

Modeling real-world things as code — classes, constructors, encapsulation, inheritance, polymorphism, abstraction, and operator overloading.

5.1 Classes & Objects

A class is a blueprint that defines what data (member variables) and behavior (member functions) something has. An object is a concrete instance created from that blueprint — you can create many objects from a single class, and each one carries its own separate copy of the data.

class Car {
public:
    string brand;
    int speed;
    void drive() { cout << brand << " is driving"; }
};

Car c1;
c1.brand = "Tesla";
c1.drive();
class Car { string brand; int speed; void drive(); } Car c1 brand='Tesla' Car c2 brand='BMW' Car c3 brand='Audi'
Figure 5.1 — One class, many independent objects

5.2 Constructors & Destructors

A constructor is a special member function that runs automatically the moment an object is created, typically used to initialize its data to sensible starting values.

A destructor runs automatically when an object is destroyed — either because it goes out of scope or is explicitly deleted — and is used to clean up resources such as heap memory or open files.

Both share the class's name; the destructor is distinguished only by a leading tilde (~).

class Car {
public:
    Car() { cout << "Car created"; }   // constructor
    ~Car() { cout << "Car destroyed"; } // destructor
};

5.3 Encapsulation

Encapsulation means bundling data together with the functions that operate on it, while hiding internal details from outside code.

In practice this means marking data members private and exposing controlled access only through public methods (commonly called getters and setters). This protects an object's internal state from being pushed into an invalid state by code outside the class.

class Account {
private:
    double balance;
public:
    void deposit(double amt) { if (amt > 0) balance += amt; }
    double getBalance() { return balance; }
};
private data (balance) deposit() withdraw() getBalance()
Figure 5.2 — Private data, accessed only through public methods

5.4 Inheritance

Inheritance lets a new class (the derived, or "child" class) reuse the fields and methods of an existing class (the base, or "parent" class), while adding or overriding its own. This models "is-a" relationships — a Dog is an Animal — and avoids rewriting logic that many related classes share.

class Animal {
public:
    void eat() { cout << "eating"; }
};

class Dog : public Animal {
public:
    void bark() { cout << "woof"; }
};

Dog d;
d.eat();  // inherited from Animal
d.bark(); // defined in Dog
class Animal (base) class Dog : public Animal class Cat : public Animal class Bird : public Animal
Figure 5.3 — Derived classes automatically get the base class's members

5.5 Polymorphism

Polymorphism ("many forms") lets code call a method through a base-class pointer or reference, while the version that actually runs is decided by the real object's type at runtime.

This requires marking the base method virtual. It is what lets you write a single function that correctly handles a Dog, a Cat, or any future Animal subclass, without knowing in advance which one it will receive.

class Animal {
public:
    virtual void speak() { cout << "..."; }
};

class Dog : public Animal {
public:
    void speak() override { cout << "Woof"; }
};

Animal* a = new Dog();
a->speak(); // "Woof" -- decided at runtime via the vtable!
Animal* a points to (runtime) Dog object speak()->'Woof' or this (runtime) Cat object speak()->'Meow'
Figure 5.4 — The correct version runs based on the actual object type (via the vtable)

5.6 Abstraction

Abstraction means exposing only what something does while hiding how it does it.

In C++ this is achieved with abstract classes: classes containing at least one pure virtual function, declared with = 0, which can never be instantiated directly and force every derived class to supply its own implementation.

class Shape {
public:
    virtual double area() = 0; // pure virtual function -> abstract class
};

class Circle : public Shape {
    double r;
public:
    Circle(double r) : r(r) {}
    double area() override { return 3.14159 * r * r; }
};

5.7 Operator Overloading

C++ lets you redefine what built-in operators such as +, ==, and << mean for your own custom classes, so objects can be combined or compared with the same natural, readable syntax used for built-in types, instead of always calling verbose named methods.

class Point {
public:
    int x, y;
    Point operator+(const Point& p) {
        return {x + p.x, y + p.y};
    }
};

Point a{1, 2}, b{3, 4};
Point c = a + b; // Uses custom operator+ -> Point{4, 6}
MODULE COMPREHENSIVE QUIZ

Module 5 Final Quiz

Test your understanding across all 7 topics of this module with interview-grade questions, tricky edge cases, and code output predictions.

Take Module 5 Final Quiz →
Yukti Mascot