2010-07-30 25 views
8
#include <stdio.h> 
int main() 
{ 
    unsigned char i=0x80; 
    printf("%d",i<<1); 
    return 0; 
} 

Pourquoi ce programme imprime-t-il 256?Valeur maximale du caractère non signé

Si je comprends bien, puisque 0x80 = 0b10000000 et unsigned char a 8 bits, le '1' devrait Overflow après Maj gauche et la sortie devrait être 0, et non 256.

+2

Vous ne voulez pas poster comme réponse parce que je ne suis pas sûr à 100%, mais n'est-ce pas parce que% d est un nombre entier? Ainsi, le code derrière les scènes assigne probablement 'i << 1' à un entier pour l'imprimer, ce qui signifie qu'il s'adapte et ne déborde pas. Essayez de faire 'printf ("% c ", i << 1);'? – Stephen

+0

@Stephen: Doit avoir posté la réponse;) – KevenK

+0

@Stephen: La sortie est vide lorsque j'utilise% c. – Variance

Répondre

14

Ceci est le résultat de C de règles de promotion d'entiers. Essentiellement, la plupart des variables entrant dans une expression sont "promues" de sorte que les opérations comme celle-ci ne perdent pas de précision. Ensuite, il est passé comme int en printf, selon les règles d'arguments variables de C.

Si vous voulez ce que vous cherchez, vous devriez jeter revenir à unsigned char:

#include <stdio.h> 
int main() 
{ 
    unsigned char i=0x80; 
    printf("%d",((unsigned char)(i<<1))); 
    return 0; 
} 

Note: L'utilisation %c comme indiqué dans le commentaire de Stephen ne fonctionnera pas parce que %c attend une entier aussi.

EDIT: Alternativement, vous pouvez le faire:

#include <stdio.h> 
int main() 
{ 
    unsigned char i=0x80; 
    unsigned char res = i<<1; 
    printf("%d",res); 
    return 0; 
} 

ou

#include <stdio.h> 
int main() 
{ 
    unsigned char i=0x80; 
    printf("%d",(i<<1) & 0xFF); 
    return 0; 
} 
+0

Pourriez-vous lancer '(i << 1)' à 'unsigned char'? – nmichaels

+0

@Nathon: N'est-ce pas ce que j'ai fait? –

+1

Bizarre, je dois allumer mes oeillères. – nmichaels

0

Ne pas oublier le format spécifique pour l'impression non signé.

printf("%u",(unsigned char)(i<<1)); 
+0

En raison des règles de promotion de C, l'argument sera très probablement passé à' printf' comme 'signed int', non' unsigned Vous devez convertir l'argument en un type correspondant au spécificateur de format. –