Desafio C
Padding e tamanho de struct
Enunciado
Crie duas structs com os mesmos campos, mas em ordens diferentes: A com char c; int i; char d; e B com int i; char c; char d;. Imprima sizeof(A) e sizeof(B) e explique a diferença causada pelo padding. Use typedef para ambas.
Requisitos
- Definir
typedef struct { char c; int i; char d; } A;etypedef struct { int i; char c; char d; } B;. - Imprimir
sizeof(A) = Xesizeof(B) = Y. - A saída deve mostrar que
sizeof(A) > sizeof(B)em plataformas típicas.
Código inicial
#include <stdio.h>
// Defina as structs A e B com typedef
int main(void) {
// Imprima os tamanhos
return 0;
}
Saída esperada
sizeof(A) = 12
sizeof(B) = 8
Ver dica
O compilador alinha int em múltiplos de 4; pense em onde ficam os buracos.
Mostrar solução
#include <stdio.h>
// Campos na ordem char, int, char: gera padding após o primeiro char
typedef struct {
char c;
int i;
char d;
} A;
// Campos agrupados: int primeiro, depois dois chars consecutivos
typedef struct {
int i;
char c;
char d;
} B;
int main(void) {
// sizeof retorna o tamanho total incluindo padding
printf("sizeof(A) = %zu\n", sizeof(A));
printf("sizeof(B) = %zu\n", sizeof(B));
return 0;
}
Passo a passo
- Em
A, o campochar cocupa 1 byte, mas oint iprecisa de alinhamento em múltiplo de 4; o compilador insere 3 bytes de padding apósc. - Depois de
i(4 bytes),char docupa 1 byte, mas a struct é alinhada ao maior campo (int), então mais 3 bytes de padding no final. - Total de
A: 1 + 3 (padding) + 4 + 1 + 3 (padding) = 12 bytes. - Em
B,int ivem primeiro (4 bytes);char cechar dficam juntos (2 bytes) e o compilador adiciona 2 bytes de padding final para alinhar a struct a 4. - Total de
B: 4 + 1 + 1 + 2 = 8 bytes. sizeofretorna o tamanho em bytes; usamos%zuporque o tipo ésize_t.
Por que funciona
O padding existe para que cada campo fique em um endereço alinhado, o que melhora o desempenho e é exigido por algumas arquiteturas. A ordem dos campos altera a quantidade de buracos: agrupar campos do mesmo tamanho reduz o desperdício. Por isso sizeof(A) é maior que sizeof(B).
Erros comuns
- Assumir que
sizeofé a soma dos campos:1+4+1=6, mas o resultado é 12. Sempre consultesizeof. - Usar
%dparasizeof: o tipo correto ésize_t, que exige%zu; caso contrário, comportamento indefinido. - Achar que o padding é igual em toda plataforma: depende do compilador e da arquitetura; os valores 12 e 8 são típicos em sistemas 64 bits com alinhamento de 4 bytes para
int.
Outra forma de resolver
Usar #pragma pack(1) elimina o padding, mas pode causar acessos desalinhados e perda de desempenho. Só use quando o layout binário for obrigatório.
Saída esperada
sizeof(A) = 12
sizeof(B) = 8