Estaba tratando de convencer a un amigo de que struct es solo un class en el C ++ moderno. Después de muchas discusiones e intercambio de recursos (incluidas algunas preguntas y respuestas de SO), se me ocurrió una idea para probarlo a través del código, así que escribí:

class A {};
struct B {};

int main()
{
    cout << (is_class<A>::value ? "Yes" : "No") << "\n";  // output Yes
    cout << (is_class<B>::value ? "Yes" : "No") << "\n";  // output Yes

    cout << (is_same<A,B>::value ? "Yes" : "No") << "\n"; // output No ???
}

Como puede ver, me sorprendió la tercera salida de línea cout. Entonces, estoy atrapado aquí ahora, y no sé si estoy en lo cierto o no.

¿Son struct y class o no? ¿Por qué el código muestra dos cosas diferentes?

Actualizar:

Entiendo bastante cuál es la diferencia entre struct y class. Lo que me confundió es la diferencia entre el is_class y el is_same como mostraron las respuestas. ¿Qué debería haber hecho si no hubiera preguntado aquí? ¿Para qué es este sitio? ¿Por qué algunos usuarios tienden a reclamar preguntas que no son útiles sin siquiera poner un comentario para especificar dónde no se ajusta a la política de preguntas?

Recuerde, no todas las personas hablan inglés con fluidez. y no todas las personas tienen años de experiencia.

Gracias por todos los que responden o comentan.

1
Kamal Zidan 18 may. 2017 a las 23:33

3 respuestas

La mejor respuesta

Al principio tienes razón. una estructura es solo una clase debajo del capó.

Algunas indicaciones:

1- Puede reenviar la declaración de uno de ellos y luego definirlo con el otro (aunque algunos cumplidores pueden emitir una advertencia).

class A;     // declaration of A with class
struct A { /* definition of A with struct */ } ;

2- is_class<> devuelve verdadero para ambos.
3- No hay is_struct<> en <type_traits>.
4- En la mayoría de los casos, las dos palabras clave son intercambiables. (por ejemplo: en enumeración de ámbito).

Sin embargo, tienen importantes diferencias sintácticas:

struct

  • Otorga acceso público a sus miembros por defecto.
  • Compatible con versiones anteriores de C si se usa sin características de C ++.

class

  • Otorga acceso privado a sus miembros de forma predeterminada.
  • No es compatible con C.

Cuál usar es una cuestión de convención y / o conveniencia.

En general, prefiero usar struct como un agregado de datos (registro). Y class para otros usos.

Ahora llegamos a su segunda pregunta:

¿Por qué el código muestra dos cosas diferentes?

No es asi.

Porque is_class<> no se trata de tipos, sino de categorías de tipos . (es decir, is_class<x> verifica si el tipo x es una clase o no) mientras que is_same<> se trata de los tipos en sí mismos ((es decir, is_same<x, y> verifica si tipo x es igual que escriba y o no))

Si cambia struct en su código de prueba en class, is_same<> aún generará "No" porque A es un tipo y B es otro tipo incluso si ambos tienen la misma categoría de tipo que es class.

De acuerdo con su código:

A a;  // a is of type A
B b; // b is of type B
// Can we say that a and b of the same type?
// No. And this is what is_same<> checks.
9
Shadi 20 may. 2017 a las 14:22

Estás confundido sobre para qué sirve std::is_same<>.

De http://en.cppreference.com/w/cpp/types/is_same:

Si T y U nombran el mismo tipo con las mismas calificaciones constantes volátiles, proporciona el valor constante del miembro igual a verdadero. De lo contrario, el valor es falso.

Claramente A y B son clases diferentes; con esa última oración, estoy insinuando que tienes razón en que un struct es lo mismo que un class; la diferencia es que un struct tiene un acceso predeterminado de public para sus miembros, mientras que un class tiene un valor predeterminado de private en su lugar.

No tome mi palabra, el estándar C ++ establece lo siguiente en 10.1.7.3 Especificadores de tipo elaborados [dcl.type.elab]:

[...] ya sea la clase o la clave de clase struct se usarán para referirse a una clase declarada usando la clase o la clave de clase struct.

Referencia: http://eel.is/c++draft/dcl.type. elab

7
user2296177 18 may. 2017 a las 21:01

Esto no tiene nada que ver con struct vs class.

cout << (is_class<A>::value ? "Yes" : "No") << "\n";  // output Yes

Sí, porque A es una clase.

cout << (is_class<B>::value ? "Yes" : "No") << "\n";  // output Yes

Sí, porque B también es una clase (it rea lly es ) .

cout << (is_same<A,B>::value ? "Yes" : "No") << "\n"; // output No ???

No, porque no son la misma clase .

A y B son dos tipos diferentes.

Es std::is_same, no std::is_similar.

3
Community 23 may. 2017 a las 12:34