2009-07-08 2 views
11

Nello spostamento a sinistra di (char) 0xff per 8 e convertendolo in int otteniamo -256 o 0xffffff00. Qualcuno può spiegare perché questo dovrebbe accadere?In C Left shift (char) 0xFF per 8 e trasmetterlo a int

#include <stdio.h> 
int main (void) 
{ 
    char c = 0xff; 
    printf("%d %x\n", (int)(c<<8),(int)(c<<8)); 
    return 0; 
} 

uscita è

-256 ffffff00 

risposta

14

char può essere firmato o non firmato, è definito dall'implementazione. Questi risultati vengono visualizzati perché char è firmato per impostazione predefinita sul compilatore.

Per il char firmato 0xFF corrisponde a -1 (è così che funziona il complemento a due). Quando si tenta di spostarlo viene prima promosso a un int e poi spostato - si ottiene in modo efficace la moltiplicazione per 256.

Così è questo codice:

char c = 0xFF; // -1 
int shifted = c << 8; //-256 (-1 * 256) 
printf("%d, %x", shifted, shifted); 
1

char non è altro che char firmato. Quindi char c = 0xFF sarà -1. Quando hai lasciato shift -1 di 8 bit ottieni -256.

+11

firma di char è l'implementazione definita. –

3

c viene promosso a un int prima della l'operazione di cambio è fatta. Supponendo che la tua implementazione faccia firmare i char per impostazione predefinita, questo significa che otterrai 0xffffffff, che verrà quindi spostato a sinistra per dare il risultato.

Se si effettua c in un carattere non firmato, è necessario ottenere ciò che si aspetta.

7

Quando ho visto per la prima volta il problema, la mia vista iniziale era che il char 'c' doveva essere spostato a sinistra 8 bit - tutti gli 8 bit scartati, il carattere vuoto sarebbe quindi convertito in un valore int di 0.

Un po 'di ricerca rivela Usual Unary Conversions - questo è dove per ridurre il numero elevato di tipi aritmetici, le conversioni vengono applicate automaticamente agli operandi di unario'! ',' - ',' ~ 'e' * ' operatori, e a ciascuno degli operandi degli operatori "< binario" < "e" >> ".

Pertanto il carattere "c" viene convertito in un int primo, quindi spostato a sinistra, fornendo la risposta che si vede.

Impara qualcosa di nuovo ogni giorno!