examples ejemplos comando cadena buscar c++ struct syntax scope-resolution

c++ - ejemplos - awk unix



¿Qué significa la sintaxis de C++ "A:: B: A{};" (2)

Esta definición

struct A { struct B; };

Define una estructura A con una declaración de una estructura anidada B 1 . El nombre completo de B es A::B , se podría decir que B está dentro del "espacio de nombres" de A Luego esto:

struct A::B : A { // Note I added spaces };

Es la definición de A::B , y el single : especifica que se deriva de A

Ahora, la parte interesante es A::B::A::B Vamos a diseccionarlo:

  1. A::B nombra la estructura anidada.
  2. A::B::A accede al nombre de clase inyectado A dentro de B La inyección se debe a la herencia.
  3. A::B::A::B nombra la estructura anidada B en A nuevamente.

Y puede continuar hasta el infinito, o al menos hasta que su compilador cumpla con su límite de traducción 2 .

Un ejercicio intelectual divertido, pero evite como la plaga en el código real.

[class.qual]/1 explica cómo funciona la búsqueda

Si el especificador de nombre anidado de un id calificado califica una clase, el nombre especificado después del especificador de nombre anidado se busca en el alcance de la clase ([class.member.lookup]), excepto en los casos enumerados abajo. El nombre representará a uno o más miembros de esa clase o de una de sus clases base (Cláusula [class.derived]).

Y el texto anterior nos permite nombrar la clase base porque [class]/2

El nombre de la clase también se inserta en el ámbito de la clase misma; Esto se conoce como el nombre de la clase inyectada . Para fines de verificación de acceso, el nombre de clase inyectado se trata como si fuera un nombre de miembro público.

Lo anterior dice claramente que comenzar un nombre completamente calificado con A:: permite especificar un miembro o una clase base. Como A no tiene bases, solo puede especificar A::B (un "tipo de miembro"). Pero A::B también nomina una clase. Por lo tanto, podemos especificar una base o miembro de eso también con A::B:: , que nos permite nombrar A::B::A Ahora enjuague y repita.

1 - Tenga en cuenta que es un B completamente diferente. Nada relacionado con la struct B global struct B
2 - Un mínimo recomendado de 256 según [implimits]/2.36

¿Qué significa la struct A::B:A {}; sintaxis de C ++ struct A::B:A {}; ¿media? ¿Dónde se describe esta definición de nombre (o acceso) en el estándar C ++?

#include <iostream> struct B; struct A { struct B; }; struct A::B:A { }; int main() { A::B::A::B b; std::cout<<"Sizeof A::B::A::B is " << sizeof(A::B::A::B)<<std::endl; return 0; }


Primero de todo struct B; es una declaración directa de la estructura B en el espacio de nombres global. Puede ser confuso porque en realidad no es relevante en este ejemplo. Se puede acceder a este B global como ::B o solo como B

struct A { struct B; };

Es una definición de la estructura A en el espacio de nombres global con una declaración directa de la estructura anidada B (no es lo mismo que B declarado previamente en el espacio de nombres global). Se puede acceder a esta B anidada como ::A::B o A::B

struct A::B:A { };

Es una definición de estructura B anidada de estructura A que hereda de A (con el especificador de acceso omitido). Se puede reescribir para:

struct A::B : public A { };

Tenga en cuenta que escribir la definición de la estructura B anidada dentro de la definición A como esta no funcionará:

struct A { struct B: A { // error: A is incomplete at this point }; };

Y finalmente A::B::A se refiere a la clase base de la estructura anidada B , es decir, a A , por lo que A::B::A::B es equivalente a solo A::B