es.davy.ai

Preguntas y respuestas de programación confiables

¿Tienes una pregunta?

Si tienes alguna pregunta, puedes hacerla a continuación o ingresar lo que estás buscando.

¿Sobrescribir una función virtual pero no una función virtual pura?

Estoy intentando derivar una clase C de dos clases, A y B; después de leer esta respuesta, intenté escribir using B::<función> para anular una función virtual pura en A con la implementación en B.

Sin embargo, el enfoque de esa respuesta no funciona para funciones virtuales puras; en ese caso, descubrí que necesitaba ser más explícito.
Entonces, evidentemente, using puede resolver la ambigüedad, ¿pero no puede introducir una implementación?
Solo esperaba entender mejor qué está sucediendo aquí.

“` cpp
struct A {
// esto resultaría en ambigüedad:
//virtual void e(void) const {} // ERROR: miembro 'e' encontrado en varias clases base

// resolviendo la ambigüedad con 'using'
virtual void f(void) const {} // OK

// esto resultaría en un método no implementado:
//virtual void g(void) const = 0; // ERROR: el tipo de variable 'C' es una clase abstracta

// *** ¿por qué esto no funciona? ***
//virtual void h(void) const = 0; // ERROR: el tipo de variable 'C' es una clase abstracta

// resolviendo la ambigüedad definiendo explícitamente lo que quiero
virtual void i(void) const = 0; // OK
};

struct B {
void e(void) const {}
void f(void) const {}
void g(void) const {}
void h(void) const {}
void i(void) const {}
};

struct C : public A, public B {
using B::f; // es suficiente para fijar 'f'
using B::h; // no es suficiente para fijar 'h'
void i(void) const { B::i(); } // es suficiente para fijar 'i'
};

int main() {
C X;
X.e();
X.f();
X.g();
X.h();
X.i();
}
“`</función>

Tags:  , , , ,

Answer

  1. Avatar for davy.ai

    La pregunta se refiere al uso de la palabra clave using para derivar una clase C de dos clases A y B, y anular una función virtual pura en A con la implementación en B. El enfoque en la respuesta enlazada no funcionó para funciones virtuales puras, y la pregunta solicita una mejor comprensión de lo que está sucediendo.

    El código proporcionado muestra que using puede resolver la ambigüedad, pero no puede introducir una implementación. Esto es evidente por el hecho de que usar B::h no es suficiente para definir h y aún así resulta en un método no implementado. Esto se debe a que using solo trae nombres de la clase base al ámbito de la clase derivada, pero no afecta a la tabla de funciones virtuales (o vtable) de la clase.

    Por lo tanto, en el caso de una función virtual pura, la clase derivada C debe proporcionar su propia implementación o heredarla de otra clase base. Esto es lo que sucede cuando C define explícitamente i como virtual void i(void) const = 0;. Esto es suficiente para definir i y el programa se compila sin errores.

    En resumen, using puede resolver la ambigüedad, pero no puede introducir una implementación para funciones virtuales puras. Una clase derivada debe proporcionar su propia implementación o heredarla de otra clase base.

Comments are closed.