c++ derived-class virtual-functions vtable

Tabla virtual C++



derived-class virtual-functions (4)

En la medida en que solo se considera la funcionalidad específica de la función virtual, en un enfoque tradicional para vtable, la clase derivada de la implementación necesitaría una versión separada de vtable si y solo si la clase derivada reemplaza al menos una función virtual. En su ejemplo, Derived anula la función virtual de print . Dado que Derived tiene su propia versión de print , la entrada correspondiente en Derived vtable es diferente de la de Base vtable. Esto normalmente requeriría un vtable separado para Derived .

Si Derived no anulara nada en absoluto, formalmente aún sería una clase polimórfica separada, pero para hacer que sus funciones virtuales funcionen correctamente, también podríamos haber reutilizado Base vtable para Derived . Por lo tanto, técnicamente no habría necesidad de una vtable separada para Derived .

Sin embargo, en implementaciones prácticas, la estructura de datos a la que generalmente nos referimos como "vtable", a menudo también contiene información adicional específica de la clase. Esa información adicional es tan específica de la clase que la mayor parte del tiempo resulta imposible compartir vtables entre diferentes clases en la jerarquía, incluso si usan el mismo conjunto de funciones virtuales. Por ejemplo, en algunas implementaciones, el puntero vtable almacenado en cada objeto polimórfico apunta a la estructura de datos que también almacena la llamada "información RTTI" sobre la clase. Por esta razón, en la mayoría de las implementaciones prácticas (si no todas), cada clase polimórfica obtiene su propia vtable, incluso si los punteros de función virtual almacenados en esas tablas son los mismos.

Leí a mucha gente escribiendo "existe una tabla virtual para una clase que tiene una función virtual declarada en ella".

Mi pregunta es, ¿existe un vtable solo para una clase que tiene una función virtual o también existe para las clases derivadas de esa clase?

p.ej

class Base{ public: virtual void print(){cout<<"Base Print/n";} }; class Derived:public Base{ public: void print(){cout<<"Derived print/n";} }; //From main.cpp Base* b = new Derived; b->print();

Pregunta: Si no hubiera habido vtable para la clase derivada, la salida no habría sido "impresión derivada". Entonces, IMO, existe una vtable para cualquier clase que tenga una función virtual declarada y también en las clases que heredan de esa clase. Es esto correcto ?


Sí, es verdad. En realidad, dada la definición de la base:

class derived:public base{ public: void print(){cout<<"derived print/n";} };

es completamente equivalente a:

class derived:public base{ public: virtual void print(){cout<<"derived print/n";} };

... porque ya definiste imprimir como virtual en base.

Desearía que el compilador hiciera cumplir eso ...


Sí, eso es verdad. Una clase hereda todos los miembros de datos de su clase base, incluido vtable. Sin embargo, las entradas de vtable se ajustan en consecuencia (por ejemplo, si la clase invalida un método virtual de clase base, la entrada correspondiente en vtable debe apuntar a su propia implementación).

Pero tenga en cuenta que el concepto de ''vtable'' es una práctica común utilizada por todos los compiladores, pero no es obligatorio ni está estandarizado.


Sí, tu entendimiento es correcto. Cualquier clase que tenga una base con cualquier función virtual tiene una vtable.