← Back to C++ Course | Chapter 17: Advanced C++ | Lesson 9 of 17

C++ dynamic_cast

What is dynamic_cast?

The dynamic_cast operator is used for safe downcasting in polymorphic class hierarchies. It checks at runtime whether a base class pointer actually points to a specific derived class object.

Example: What is dynamic_cast?

cpp
#include <iostream>

class Animal {
public:
	virtual ~Animal() {}
};

class Dog : public Animal {};

int main() {
	Animal *a = new Dog();
	Dog *d = dynamic_cast<Dog *>(a);
	std::cout << (d != nullptr) << std::endl;
	delete a;
	return 0;
}

Casting with References

You can also use dynamic_cast with references. Because there is no such thing as a null reference, dynamic_cast throws a 'std::bad_cast' exception if the conversion fails.

Example: Casting with References

cpp
#include <iostream>

class Animal {
public:
	virtual ~Animal() {}
};

class Dog : public Animal {};

int main() {
	Dog realDog;
	Animal &a = realDog;
	try {
		Dog &d = dynamic_cast<Dog &>(a);
		std::cout << "Cast succeeded" << std::endl;
	} catch (std::bad_cast &e) {
		std::cout << "Cast failed" << std::endl;
	}
	return 0;
}

Requirement of Polymorphism

For dynamic_cast to work, the base class must be polymorphic. This means the base class must declare at least one virtual function, such as a virtual destructor.

Example: Requirement of Polymorphism

cpp
#include <iostream>

class Animal {
public:
	virtual ~Animal() {}
};

class Dog : public Animal {};

int main() {
	Animal *a = new Dog();
	Dog *d = dynamic_cast<Dog *>(a);
	std::cout << (d != nullptr) << std::endl;
	delete a;
	return 0;
}

Upcasting vs Downcasting

Upcasting converts a derived pointer to a base pointer and is handled implicitly by the compiler. Downcasting converts a base pointer to a derived pointer and requires an explicit dynamic_cast to perform runtime checks.

Example: Upcasting vs Downcasting

cpp
#include <iostream>

class Animal {
public:
	virtual ~Animal() {}
};

class Dog : public Animal {};

int main() {
	Dog d;
	Animal *a = &d;
	Dog *back = dynamic_cast<Dog *>(a);
	std::cout << (back != nullptr) << std::endl;
	return 0;
}

Downcasting Best Practices

Always check if the returned pointer from a dynamic_cast is nullptr before using it. This prevents your program from crashing if the cast fails at runtime.

Example: Downcasting Best Practices

cpp
#include <iostream>

class Animal {
public:
	virtual ~Animal() {}
};

class Dog : public Animal {};
class Cat : public Animal {};

int main() {
	Animal *a = new Cat();
	Dog *d = dynamic_cast<Dog *>(a);
	if (d == nullptr) {
		std::cout << "Not actually a Dog" << std::endl;
	}
	delete a;
	return 0;
}

Login to run this code

C/C++/Java/PHP execution requires a free account. Your code is saved — you'll land right back in the editor after logging in.