2009-11-27 39 views
8

Tengo algunos problemas con el uso del operador condicional para obtener una referencia a un objeto. Tengo la una configuración similar a esto:Problema del operador condicional

class D 
{ 
    virtual void bla() = 0; 
}; 

class D1 : public D 
{ 
    void bla() {}; 
}; 

class D2 : public D 
{ 
    void bla() {}; 
}; 

class C 
{ 
public: 
    C() 
    { 
     this->d1 = new D1(); 
     this->d2 = new D2(); 
    } 

    D1& getD1() {return *d1;}; 
    D2& getD2() {return *d2;} 
private: 
    D1 *d1; 
    D2 *d2; 
}; 

int main() 
{  
    C c;  
    D& d = (rand() %2 == 0 ? c.getD1() : c.getD2());  
    return 0;  
} 

Al compilar, esto me da el siguiente error:

WOpenTest.cpp: In function 'int 
main()': WOpenTest.cpp:91: error: no 
match for conditional 'operator?:' in 
'((((unsigned int)rand()) & 1u) == 0u) 
? c.C::getD1() : c.C::getD2()' 

entiendo que esto es ilegal de acuerdo con el estándar de C++ (as seen in this blog post), pero don No sé cómo obtener mi referencia al D sin usar el operador condicional.

¿Alguna idea?

Respuesta

14

moldeada a D& dentro de ambas ramas:

D& d = (rand() %2 == 0 ? static_cast<D&>(c.getD1()) : static_cast<D&>(c.getD2())); 
+0

Sí, esto funciona perfectamente. – laura

+1

Solo necesita uno de los moldes aquí también, lo que hace que la expresión sea un poco menos detallada. –

+0

@Richard, ah buena nota. Para mí, parece más fácil si aplico el elenco a ambos operandos, pero, por supuesto, es correcto, un lanzamiento es suficiente para que el compilador vea que el otro se puede convertir a 'D &' implícitamente. –

2

Por cierto, que realmente no necesita utilizar un operador condicional,

D* dptr; if(rand() %2 == 0) dptr = &c.getD1(); else dptr = &c.getD2(); 
D& d = *dptr; 

funcionaría también.

+0

Esto parece ser un poco derrochador. ¿Hay algún beneficio en este enfoque frente al operador ternario? –

+0

Esto es cierto, pero creo que el código parece torpe si lo haces (utilizando la referencia se ve más limpio). – laura

+1

Stephen, solo estaba dando una respuesta en respuesta a OP "pero no sé cómo obtener mi referencia a D sin utilizar el operador ternario" –

0

O puede cambiar los tipos de devolución de las funciones a la Clase base.

+0

Esto aderezará el resto del código usando los dos getters con moldes dinámicos, no es realmente una solución – laura

+0

tiene razón, static_cast debería funcionar. – shyam