Pregunta

el uso de la declaración no parece funcionar con el tipo de enumeración

class Sample{
public:
enum Colour { RED,BLUE,GREEN};
}

using Sample::Colour;

no funciona !! ¿necesitamos agregar usando la declaración para cada enumerador de tipo enum? como abajo

using sample::Colour::RED;
¿Fue útil?

Solución

Una clase no define un espacio de nombres, por lo tanto " usando " no es aplicable aquí.

Además, debe hacer pública la enumeración.

Si está intentando usar la enumeración dentro de la misma clase, aquí hay un ejemplo:

class Sample {
 public:
  enum Colour { RED, BLUE, GREEN };

  void foo();
}

void Sample::foo() {
  Colour foo = RED;
}

Y para acceder desde fuera de la clase:

void bar() {
  Sample::Colour colour = Sample::RED;
}

Otros consejos

Para agregar a la respuesta de Stevela, el problema con el código original es que usted referirse a un miembro, pero la declaración de uso no es en sí misma una declaración de miembro:

7.3.3 / 6 tiene:

  

Una declaración de uso para un miembro de la clase   será una declaración de miembro.

Para resaltar esto, el siguiente ejemplo funciona:

class Sample
{
public:
  enum Colour { RED,BLUE,GREEN};
};

class Derived : public Sample
{
public:
  using Sample::Colour;  // OK
};

Finalmente, como señaló Igor Semenov aquí , incluso si mueve el definición de enumeración en un espacio de nombres, lo que permite la declaración de uso, la declaración de uso solo declarará el nombre del tipo de enumeración en el espacio de nombres (la referencia estándar de 2003 es 7.3.3 / 2).

namespace Sample
{
  enum Colour { RED,BLUE,GREEN};
}

using Sample::Colour;
using Sample::BLUE;


void foo ()
{
  int j = BLUE; // OK
  int i = RED;  // ERROR
}

Tipos de base dependientes

Para permitir especializaciones parciales y explícitas, cuando el compilador analiza una plantilla de clase no realiza ninguna búsqueda en clases base dependientes. Como resultado, la siguiente variación con Muestra como plantilla no se compila:

template <typename T>
class Sample
{
public:
  enum Colour { RED,BLUE,GREEN};
};

template <typename T>
class Derived : public Sample<T>
{
public:
  using Sample<T>::Colour;  // What kind of entity is Colour?

  Colour foo ()     // Not OK!
  {
  return this->RED;
  }
};

El problema es que Derived::Colour es tratado como un objeto por el compilador (14.6 / 2):

  

Se supone que un nombre usado en una declaración o definición de plantilla y que depende de un parámetro de plantilla no nombra un tipo a menos que la búsqueda de nombre aplicable encuentre un nombre de tipo o el nombre sea calificado por la palabra clave typename.

Observando las dos condiciones para que el nombre sea un tipo:

  1. La búsqueda de Colour no encuentra un tipo porque la base dependiente Sample<T> no se busca.
  2. El nombre no está calificado por typename

Por lo tanto, el ejemplo necesita la palabra clave <=>:

template <typename T>
class Derived : public Sample<T>
{
public:
  using typename Sample<T>::Colour;  // Colour is treated as a typedef-name

  Colour foo ()  // OK
  {
  return this->RED;
  }
};

Nota: la versión '98 del estándar no permitía que <=> se usara con una declaración de uso y, por lo tanto, la solución anterior no era posible. Consulte Acceso a tipos desde clases base dependientes y CWG11 .

Estándar C ++, 7.3.3.1:

  

El nombre del miembro especificado en un   utilizando-declaración se declara en el   región declarativa en la que el   aparece la declaración de uso. [ Nota:   solo el nombre especificado es así   declarado; especificando una enumeración   nombre en una declaración de uso no   declarar sus enumeradores en el   utilizando-declaración & # 8217; s declarativo   región. & # 8212; nota final]

Licenciado bajo: CC-BY-SA con atribución
No afiliado a StackOverflow
scroll top