c ++依赖于派生类的纯虚函数

时间:2017-11-19 06:48:24

标签: c++ inheritance derived-class pure-virtual

我正在开发一个边界框/碰撞检测系统,我使用不同类型的边界卷,id像所有边界卷一样派生相同的基类,然后使用纯虚函数强制所有派生类实现基本函数像

  • isCollidingWith(BoudingBox)

但是这就是给我带来麻烦的东西:我想让它们为每个BoudingVolume类型实现一个函数。因此,如果我有一个边界框和一个边界球,那么球类和框类都应该实现

  • isCollidingWith(BoundingBox)
  • isCollidingWith(BoundingSphere)

如果我然后创建一个新的BoundingVolume,如BoundingCylinder(通过从基类派生),我希望编译器抛出一个错误,直到BoundingBox和BoundingSphere为新的isCollidingWith函数实现{1}}类型(以及CylinderCylinderisCollidingWithBox Sphere实施Cylinder之前的类型。

我不确定如何实现这一点,但我想过使用CRTP。 这甚至可能吗?

2 个答案:

答案 0 :(得分:4)

当你在基类中创建纯虚函数时,对于它的实现派生类它是必须,如果派生类没有实现它那么编译器会给你一个错误。因此,您不必注意是否实现了纯虚函数。

答案 1 :(得分:1)

可以用CRTP编写这样的东西

class BoundingBox;
class BoundingSphere;

class Shape
{
    public:
        virtual bool isIntersecting(const BoundingBox&) const = 0;
        virtual bool isIntersecting(const BoundingSphere&) const = 0;
};

class BoundingVolumeBase
{
    public:
        virtual bool checkIntersection(const Shape&) const = 0;
        virtual ~BoundingVolumeBase();
};

template<class Derived>
class BoundingVolume : public BoundingVolumeBase
{
        bool checkIntersection(const Shape& shape) const override
        {
            return shape.isIntersecting (static_cast<const Derived&>(*this));
        }
};

class BoundingBox : public BoundingVolume<BoundingBox> {
    // ...
};

class BoundingSphere : public BoundingVolume<BoundingSphere> {
    // ...
};

现在,如果我们发明了一种新的BoundingVolume,那么在将新函数添加到Shape之前,它将无法编译。

class BoundingCylinder : public BoundingVolume<BoundingCylinder> {
    // ...
};

BoundingCylinder bc; // <-- this will not compile

没有必要这样做。任何使用虚函数作为唯一类型的基于类型的调度的方法都可以工作(无论如何,你最终可能会得到与上面大致相同的东西)。如果您依赖typeid或自定义类型标识符,则可能会遇到问题。

此方法的缺点是类Shape所有具体类型BoundingVolume的相互依赖。