Skip to content
AgileLogics
5 min read

Polymorphism & Virtual Functions

Prerequisites: Inheritance

Unlike Java (where every method is effectively overridable by default), C++ requires the virtual keyword to opt a method into being overridden polymorphically:

class Animal {
public:
    virtual void makeSound() {
        std::cout << "Some generic sound" << std::endl;
    }
    virtual ~Animal() = default; // virtual destructor — see below
};

class Dog : public Animal {
public:
    void makeSound() override {
        std::cout << "Woof!" << std::endl;
    }
};

Animal *a = new Dog();
a->makeSound(); // Woof! — the Dog version runs, via the base pointer
delete a;

override isn't required, but documents intent and catches a typo (a misspelled override silently becomes an unrelated new method without it). A base class with any virtual function should almost always give its destructor virtual too — otherwise, deleting a derived object through a base pointer skips the derived class's destructor, a real and common bug.

Common mistakes

  • Forgetting virtual on the base method and expecting the derived version to run through a base pointer/reference — without it, the base version always runs instead, regardless of the object's actual type.