2010-02-02 32 views
6

tengo la siguiente jerarquía de clases:compilador de C++ con CRTP

template <typename T> 
class base 
{ 
public: 
    void f() {} 
}; 

class class_a : public base<class_a> {}; 

class class_b : public base<class_b>, 
       public class_a 
{ 
    using base<class_b>::f; 
}; 

int main() 
{ 
    class_b b; 
    b.f(); 
    return 0; 
} 

COMEU e Intel C++ reclamo v11 todo está bien, sin embargo GCC (4.4.1) y VC++ 2008 parecen quejarse (http://codepad.org/KQPDsqSp), por ejemplo, :

g++ -pedantic -Wall -o test test.cpp 
test.cpp: In function ‘int main()’: 
test.cpp:5: error: ‘void base<T>::f() [with T = class_b]’ is inaccessible 
test.cpp:14: error: within this context 

creo que el código está bien formado, ya que es, sin embargo, podría estar equivocado, estoy esperando que alguien de la comunidad SO C++ podría proporcionar alguna información sobre este tema.

Nota: Al agregar "public" antes de la directiva using en class_b, se resuelve el problema tanto para gcc como para VS. ¿Debe la sección de acceso de la clase en la que se aplica la directiva de uso prevalecer sobre el modo de derivación (público, privado) de la clase base?

En este corto es

  • un error del compilador - si es así, que GCC, VS o COMEU compilador, Intel
  • es el código de arriba bien formado?
  • ¿La sección de acceso en la que se utiliza una directiva de uso anula el modo de derivación de la base?

Respuesta

3

Lo que está haciendo aquí, es resolver una ambigüedad importando el símbolo en las clases privada de espacio de nombres. Por lo tanto, se trata de seguir el método y cambiar su visibilidad a privada. No puede tener dos funciones con el mismo prototipo, tanto privado como público, por lo tanto, f es ahora privado.

Al menos GCC cree que using should be able to change the visibility de una función.

Las referencias vagas, sin embargo, se encuentran en GCC bug database, muestran que el uso no debe verse afectado por el alcance.

Lo más importante es una respuesta directa (C++ estándar '03 - 7.3.3/15)

El alias creado por el uso de la declaración-tiene la accesibilidad habitual para un miembro-declaración.

De ahí que las respuestas serían:

  • que un error en Comeau
  • no, el código no está bien formada, al menos, C++ 03-sabia (no se puede encontrar nada relacionado en C++ 0x N3000)
  • sí, se puede cambiar el ámbito de acceso
+0

Nada está en un espacio de nombres privado o alcance. y la directiva de uso no considera la parte de acceso de la clase en la que se llama, sin embargo, agregar público antes de la directiva de uso resuelve el problema. Creo que en este caso, gcc y VS tienen la culpa, ¿no crees? –

+2

@darid, en el enlace proporcionado arriba verá que, al menos en el caso de GCC, cambió a la forma en que ahora es explícita. –

+0

@Kornel: esa es una respuesta excelente, me gustaría añadir que lo he probado con el compilador intel C++ y me gusta Comeau.Me pregunto si es un problema de interfaz de analizador, Intel y Comeau obtienen el suyo de EDG, pero también lo hace MS para VSC++, que simplemente confunde las cosas todo eso más. –