在C ++中是否可以让多个类共享一个vtable? 根据我的理解,如果一个类有一个虚函数,那么它将生成一个vtable。所以每个类都应该有自己的vtable。
答案 0 :(得分:6)
Vtables是一个实现细节。 C ++没有vtables,它有虚函数。 Vtables恰好是最常见的(如果不是唯一的)实现,细节也不同。
你真正想要实现的目标是什么?
答案 1 :(得分:2)
多态性可以通过多种方式实现。 vtable也可以通过多种方式实现。但通常在以下情况下
class A {
virtual foo(){}
}
class B : public A {
virtual foo(){}
}
class C : public B {
void fooNonVirtual(){};
}
类B
和C
应该具有相同的vtable。
示例:
A *a = new A;
B *b = new B;
C *c = new C;
a->foo(); // A::foo is called
((A*)b)->foo(); // B::foo is called
((A*)c)->foo(); // B::foo is called
foo
和a
的 b
调用不同的方法,因为A和B具有不同的vtable。对于b
和c
,调用相同的方法。因此编译器可以进行一些优化,并且只为B和C类创建一个vtable。
fooNonVirtual
不是虚拟的,根本不需要vtable。
答案 2 :(得分:0)
你可以做到
typedef some::Class AnotherClass;
然后这些类将共享。
此外,继承可以 - 至少在理论上 - 导致共享vtable。
答案 3 :(得分:0)
vtable基本上是一个虚函数表,所以如果这两个类具有相同的虚函数,那么共享vtable似乎非常简单。
struct Class1
{
virtual void func() { /* whatever */ }
};
struct Class2 // can share the vtable with Class1
{
void nonvirtual_func() { /* whatever */ }
};
但是,vtable也可能包含其他信息(例如typeid
返回的内容) - 在这种情况下,共享vtable是不可能的。有些编译器可以选择禁用RTTI和typeid
- 这样设置可能会影响问题的答案。
答案 4 :(得分:0)
要问的是什么并不是很清楚。单个班级可以
有许多不同的vtable
,具体取决于它的使用方式。和
编译器将合并几个类的vtable
层次结构。例如:
struct VB { virtual ~VB() = default; };
struct L : virtual VB {};
struct R : virtual VB {};
struct D : L, R {};
在这种情况下,VB
的vtable会有所不同
取决于您是否实例化L
,R
或D
。
另一方面,在派生类型D
最多的对象中,
D
和基类L
可能共享相同的内容
vtable
。