A class is polymorphic if it has at least one virtual method (of its own or inherited).
When does it create VTable?
Ok so first let's get the elefant out of the room. The standard doesn't require Virtual Tables and intentionally leaves open the method of implementing dynamic polymorphism. In this case it just defines rules of behavior, but doesn't mandate any method of implementing said behavior. See Alternatives to vtable , Alternative virtual mechanism implementations? or Comparison with alternatives. They are an interesting read. Now that the elephant is out of the room in practice most of (if not all of) C++ compilers implement polymorphism through the vtables mechanism.
A polymorphic class will have a virtual table. And the discussion could easily end here.
However there is an interesting (mostly academic) case to consider: virtual inheritance without polymorphic objects.
E.g.:
struct A {};
struct B : virtual A {};
struct C : virtual A {};
struct X : B, C { };
None of the above classes(*) are polymorphic. I.e.
static_assert(!std::is_polymorphic<B>::value);
static_assert(!std::is_polymorphic<C>::value);
static_assert(!std::is_polymorphic<X>::value);
because we don't have any virtual methods.
The question is now if we have a vtable for for above classes.
And again the method of implementing virtual inheritance is implementation defined.
And honestly I don't know the answer to this.
Both gcc
and clang
have:
| | 32 bit | 64 bit |
| --------- | ------ | ------ |
| sizeof(A) | 1 | 1 |
| sizeof(B) | 4 | 8 |
| sizeof(C) | 4 | 8 |
| sizeof(X) | 8 | 16 |
Which suggest that B and C each contain a pointer which are inherited by X
. From what I can remember and reason about those are not pointers to vtables, but pointers (or offsets) that point to the interior of the structure, but I can't tell for sure.
(*) I take this opportunity again to mention that an entity declared with the struct
keyword is a class.