Merci de poster votre code. Maintenant, je vois le problème. C'est à cause du rembourrage.À savoir:
printf("sizeof(char): %d\n", sizeof(char));
printf("sizeof(short): %d\n", sizeof(short));
printf("sizeof(int): %d\n", sizeof(int));
printf("sizeof(struct st): %d\n", sizeof(struct st));
Sur ma machine, cette imprimante
1
2
4
8
Vous pourriez penser, ne devrait pas être sizeof(struct st)
1 + 2 + 4 = 7
? C'est certainement une pensée raisonnable, mais à cause de alignment issues il y a padding entre a
et c
. Par conséquent, en mémoire, le struct ressemble à la suivante (par rapport au premier octet du struct):
0x00000000: char a
0x00000001: padding
0x00000002: first byte of short c
0x00000003: second byte of short c
0x00000004: first byte of int b
0x00000005: second byte of int b
0x00000006: third byte of int b
0x00000007: fourth byte of int b
En conséquence (par rapport à &s1
):
&s1.b - 1 is ((long)&s1.b) - sizeof(int) = 4 - 4 = 0 = &s1
C'est pourquoi les deux &s1
et &s1.b - 1
imprimera la même adresse. En particulier, si
&s1 = 0x804a01c
puis
&s1.b = 0x804a01c + 0x00000004 = 0x804a020
et
&s1.b - 1 = 0x804a020 - 0x00000004 = 0x804a01c
et
&s1.b - 2 = 0x804a020 - 0x00000008 = 0x804a018
Notez enfin que ce comportement est spécifique à la mise en œuvre. Ce n'est pas portable!
Le remplissage de structure est défini par l'implémentation. –
@Prasoon: cela n'a rien à voir avec le remplissage de la structure: '& s1.b' est un' int * ', et le remplissage de la structure n'a aucun effet sur le fonctionnement de l'arithmétique du pointeur avec un' int * '. –
@Steve Jessop: Exactement. Plus un sur votre commentaire. – jason