非多态派生类的基类
Base class of non polymorphic derived classes
我有以下类定义:
class BaseHandle { /* Lots of things */ };
class VertexHandle : public BaseHandle {
/* Only static members and non-virtual functions, default dtor */ };
class EdgeHandle : public BaseHandle { /* Dito */ };
class FaceHandle : public BaseHandle { /* Dito */ };
所有类都没有虚函数或基。
派生类仅派生自BaseHandle
,不添加任何非静态成员,也不添加非默认 dtor。
我想在同一向量中保存Vertex-
、Edge-
和FaceHandles
:
std::vector<BaseHandle*> handles;
但是它不起作用,如果我检索BaseHandle
对象并想将它们dynamic_cast
派生对象,它会失败,因为这些类不是多态的(这是我的解释,也许我错了)。
如何实现BaseHandles
的共同向量?我应该提到,我不能更改类定义,因为它们是第三方库的一部分。
你需要在父类中有一个虚拟析构函数才能多态地使用它
class BaseHandle
{
public:
virtual ~BaseHandle();
...
};
这是因为dynamic_cast
使用 RTTI(运行时类型信息),该信息仅在您的类至少有一个虚拟成员函数时才可用
这也将防止资源泄漏,否则只会销毁实例的父类部分
解决方法
您可以使用std::shared_ptr
std::vector
,您不仅可以通过不必手动调用new
和delete
来避免内存泄漏,而且智能指针还具有神奇的属性(它存储删除器以根据其构造方式调用销毁)来解决您的问题:
int main()
{
std::vector<std::shared_ptr<BaseHandle>> shared_vec;
shared_vec.push_back(std::make_shared<VertexHandle>());
} // At the end of scope all destructors are called correctly
如果您无法访问 c++11,您可以使用boost::shared_ptr
你可以存储
struct thing
{
enum Type { vertex, edge, face };
Type type;
union
{
VertexHandle * vh;
EdgeHandle * eh;
FaceHandle * fh;
};
};
但这基本上是一团糟...您确定要这样做吗? 看起来您在单个数组中存储了多个类型,尽管事实上无法多态地使用它们,那么实际上是否有充分的理由只有一个数组,而不是三个数组?
继Kerrek的评论之后。您可以"创建自己的并行类层次结构,并将每种类型添加为成员"。例如:
class MyBaseHandle {
public:
virtual ~MyBaseHandle(){}
virtual Box getBoundingBox() const = 0;
};
class MyEdgeHandle : public MyBaseHandle {
std::unique_ptr<EdgeHandle> handle_;
public:
MyHandle(std::unique_ptr<EdgeHandle> handle) : handle_(std::move(handle)) {}
Box getBoundingBox() const override;
};
然后,如果需要,您可以dynamic_cast
。但我会尽量避免使用dynamic_cast
。在并行类层次结构中添加virtual
方法,以执行所需的操作。例如,我向基类添加了一个 virtual getBoundingBox
函数,然后您可以专门针对特定类型的句柄:
Box MyEdgeHandle::getBoundingBox() const {
// Get data from EdgeHandle
auto v1 = handle_->getVertex1();
auto v2 = handle_->getVertex2();
// create box from edge data...
return box;
}
现场演示
如果从BaseHandle
派生的所有类都只使用来自BaseHandle
的单一继承(加上可能从具有普通 dtor 的空类继承,这些空类受空基类优化的影响),并且除了非virtual
函数和static
成员之外不添加任何内容,并且所有派生类都使用默认 DTOR 或等效项,则可以只static_cast
目标。
尽管请注意,没有办法知道它实际上是哪个派生类(如果有的话)。
- 指向基类派生类的 std::unique_ptr 的指针
- 从多个模板化基类派生时出现"隐藏重载的虚函数"警告
- 从模板基类派生是否在派生类声明的点实例化模板
- 使从一个基类派生的类能够使用继承的受保护成员
- C++多态性访问基类派生类字段
- C++派生类的设置属性到从同一基类派生的未知类对象
- 使用void* 参数定义纯虚函数的抽象基类.派生类匹配参数是指向某种类型的指针
- 在C++中,如何使用将保存从基类派生的任何对象的类成员
- 如何测试从依赖于外部系统的外部基类派生的类
- 如何从模板基类派生非模板类
- 在派生类中使用声明并不能隐藏从基类派生的相同函数
- 从具有静态结构的基类派生
- 具有从 c++ 中的非模板基类派生的模板类的事件系统
- C++ 调用从基类派生的覆盖函数
- 不清楚如何在从抽象基类派生的类中实现运算符重载
- 如何正向声明从正向声明的模板基类派生的类
- 是否可以从 std::enable_shared_from_this 和抽象基类派生
- 多态性c++,试图访问从抽象基类派生的类的成员函数
- C++多重继承,基类派生自同一类
- 基类派生类访问-如何