在C++中,类型擦除通常是通过虚函数实现的。虚函数允许你在基类中定义一个接口,然后通过派生类来覆盖这个接口。这样,当你使用基类指针或引用调用虚函数时,实际调用的函数将由对象的实际类型决定。这里有一个简单的例子来说明如何使用虚函数实现类型擦除:
#include <iostream>
#include <string>
// 基类
class Shape {
public:
// 虚函数,用于计算面积
virtual double area() const = 0;
// 虚析构函数,确保派生类的析构函数被正确调用
virtual ~Shape() = default;
};
// 派生类:圆形
class Circle : public Shape {
public:
Circle(double radius) : radius_(radius) {}
// 覆盖基类的虚函数
double area() const override {
return 3.14159 * radius_ * radius_;
}
private:
double radius_;
};
// 派生类:矩形
class Rectangle : public Shape {
public:
Rectangle(double width, double height) : width_(width), height_(height) {}
// 覆盖基类的虚函数
double area() const override {
return width_ * height_;
}
private:
double width_;
double height_;
};
int main() {
Shape* shape1 = new Circle(5.0);
Shape* shape2 = new Rectangle(4.0, 6.0);
std::cout << "Circle area: " << shape1->area() << std::endl;
std::cout << "Rectangle area: " << shape2->area() << std::endl;
delete shape1;
delete shape2;
return 0;
}
在这个例子中,我们定义了一个名为Shape
的基类,其中包含一个纯虚函数area()
。然后,我们创建了两个派生类Circle
和Rectangle
,分别表示圆形和矩形。这两个派生类都覆盖了area()
函数,以提供各自的实现。
在main()
函数中,我们使用基类指针shape1
和shape2
分别指向Circle
和Rectangle
对象。当我们调用area()
函数时,实际调用的函数将由对象的实际类型决定。这就是类型擦除的基本原理。