lenguaje funciones estructuras estructura entre ejemplo diferencia dev con arreglo anidadas c standards anonymous structure c11

entre - funciones con estructuras en c



Inicialización de estructuras anónimas o uniones en C1X. (3)

Tengo la siguiente pregunta: ¿Cómo se inicializan correctamente las estructuras anónimas (o sindicatos) de acuerdo con el borrador C1X actual? ¿Es esto legal?

struct foo { int a; struct { int i; int j; }; int b; }; struct foo f = { 1, 2, 3, 4 }; struct foo g = { 1, { 2 }, 3 };

En GCC, gj == 0 y gb == 3 , mientras que en tcc gj == 3 y gb == 0 . El borrador actual dice:

"los miembros sin nombre de los objetos de estructura y tipo de unión no participan en la inicialización. Los miembros sin nombre de los objetos de estructura tienen un valor indeterminado incluso después de la inicialización".

¿Puede esto ser realmente cierto? No es

struct foo h = { 0 };

¿Se supone que todos los miembros están en 0?

¡Muchas gracias!

ACTUALIZACIÓN :

Dado que los miembros anónimos solo parecen ser útiles al mezclar estructuras / uniones, cómo inicializar esto correctamente:

struct bar { int tag; union { double d; int i; }; };

? Esto da errores en gcc <4.6 e icc 11, pero funciona en gcc 4.6, icc 12, clang y tcc:

struct bar a = { .tag = 1, .i = 42 };

Esto da errores en clang y tcc, pero funciona en gcc y icc:

struct bar b = { .tag = 1, { .i = 42 } };

¿Es el segundo una violación de la norma?


No he leído el borrador, estoy bastante seguro de que los miembros anónimos y anónimos son diferentes. Sin nombre sería algo como

struct foo { int bar:1; /* named */ int :31; /* unnamed */ };


Todos los miembros que tienen nombres en su estructura pueden inicializarse. Simplemente no puedes inicializar las estructuras intermedias como tales. Pero

struct foo f = { .a = 1, .i = 2, .j = 3, .b = 4 };

Deberías hacerlo.


f y h deben inicializar correctamente todos los miembros, ya que i y j deben tratarse como miembros de struct foo (C1x 6.7.2.1 §13):

Los miembros de una estructura o unión anónima se consideran miembros de la estructura que contiene o unión.

No creo que la inicialización de gcc de g sea ​​correcta, considerando C1x 6.7.9 §9:

Excepto cuando se indique explícitamente lo contrario, para los fines de esta subcláusula, los miembros sin nombre de los objetos de estructura y tipo de unión no participan en la inicialización.

El §20, que se ocupa de los subagregados, no contiene ninguna declaración explícita relevante para el problema, por lo que mi mejor conjetura sería que el §9 se aplica (¡pero solo al agregado en sí, no a sus miembros!).

La conclusión es que los subagregados anónimos no existen como objetos separados, es decir, el comportamiento de tcc debería ser correcto ...

Código de ejemplo para mi toma en el tema:

struct foo { struct bar { int i; }; // (1) unnamed, but tagged, ie *not* anonymous struct { int j; }; // (2) unnamed, but anonymous struct { int k; } baz; // (3) named, but not tagged };

(1) no toma parte en la inicialización, (2) se inicializa como si struct foo tuviera un miembro adicional llamado j , (3) se inicializa como un subagregado regular.

Si mi interpretación es correcta, las estructuras anónimas solo tienen sentido si están contenidas dentro de una unión: una estructura anónima dentro de una estructura es indistinguible de una estructura plana que contiene miembros adicionales.