C++ Program using Base Abstract Class
// the OOP version in C++
#include <iostream>
// base abstract class. that is what we use as the interface
class Animal
{
public:
Animal(char const* name): m_name(name) {}
// this is required to properly delete virtual classes
virtual ~Animal() {}
// with this strange syntax we define an unimplemeted "interface" function
virtual void make_sound() = 0;
protected:
// shared data field
std::string m_name;
};
// derived class. that means that Dog is a more refined version of Animal
// you usually inherit from only a single base class
class Dog: public Animal
{
public:
// need to forward the constructor arguments
Dog(char const* name): Animal(name) {}
// here we implement the interface
void make_sound() override
{
std::cout << m_name << " the dog said: bork!" << std::endl;
}
// type-specific method
void wag()
{
std::cout << "*" << m_name << " wags*" << std::endl;
}
};
// same as above, but with a different implementation
class Cat: public Animal
{
public:
Cat(char const* name): Animal(name) {}
void make_sound() override
{
std::cout << m_name << " the cat said: mow!" << std::endl;
}
void purr()
{
std::cout << "*" << m_name << " purrs*" << std::endl;
}
};
// We can now use Animal as the general type
// There is runtime type information that allows this (dynamic dispatch)
void animal_sound(Animal& a)
{
// method called via the generic interface
a.make_sound();
// type information is still there, we can extract the original type by
// probing if dynamic cast works
auto d = dynamic_cast<Dog*>(&a);
if (d != nullptr)
d->wag();
auto c = dynamic_cast<Cat*>(&a);
if (c != nullptr)
c->purr();
}
// we can do static dispatch too, via templates (duck typing)
template <typename T>
void animal_sound_1(T& a)
{
a.make_sound();
// however, we can't easily access type information here without
// using specialization..
}
// ..and that's pretty much equivalent to overloading the function
// this works by making two different functions with internally mangled names
// for each argument combination
void animal_sound_2(Dog& a) { a.make_sound(); a.wag(); }
void animal_sound_2(Cat& a) { a.make_sound(); a.purr(); }
int main()
{
auto cat = Cat("kitty");
auto dog = Dog("puppy");
animal_sound(cat);
animal_sound(dog);
animal_sound_1(cat);
animal_sound_1(dog);
animal_sound_2(cat);
animal_sound_2(dog);
return 0;
}
Comments
Post a Comment