2010-05-11 18 views
8

Quello che so di valori numerici senza segno (unsigned short, int e lunghi), che contiene solo i numeri positivi, ma il seguente programma semplice assegnato con successo un numero negativo per un unsigned int:int Perché non firmato conteneva numero negativo

1 /* 
    2 * ===================================================================================== 
    3 * 
    4 *  Filename: prog4.c 
    5 * 
    6 * ===================================================================================== 
    7 */ 
    8 
    9 #include <stdio.h> 
10 
11 int main(void){ 
12 
13  int v1 =0, v2=0; 
14  unsigned int sum; 
15  
16  v1 = 10; 
17  v2 = 20; 
18  
19  sum = v1 - v2; 
20  
21  printf("The subtraction of %i from %i is %i \n" , v1, v2, sum); 
22  
23  return 0; 
24 } 

il risultato è: The subtraction of 10 from 20 is -10

+4

Inoltre, il tuo messaggio è fuorviante. Dovrebbe dire "La sottrazione di ** 20 ** da ** 10 ** è ..." che è ciò che stai calcolando. –

+0

Non sto cercando una soluzione per un problema del genere, voglio capirne l'idea. –

+0

Possibile duplicato di [C Unsigned int che fornisce un valore negativo?] (Http://stackoverflow.com/questions/1831753/c-unsigned-int-providing-a-negative-value) –

risposta

22

%i è l'identificatore di formato di firmata intero; è necessario utilizzare %u per stampare un numero intero senza segno.

+2

Ricorda, perché i valori non firmati possono solo memorizzare valori non negativi, sottraendo un intero senza segno da un altro comporterà un underflow se il minuend è più piccolo del sottraendo, quindi otterrete un underflow. Date un'occhiata: http://www.topbits.com/integer-overflow.html – LandonSchropp

1

Poiché valore int senza segno che è memorizzato nella somma viene trattato come intero decimale firmato a printf %i

8

Con printf, il formato %i uscita un signed int. Utilizzare %u per emettere un unsigned int. Questo è un problema comune quando si inizia la programmazione in C. Per rispondere alla domanda, il risultato di v1 - v2 è -10, ma sum è un unsigned int, quindi la risposta reale è probabilmente qualcosa come 4294967286 (2 - 10). Guarda cosa ottieni quando usi The subtraction of %i from %i is %u \n. :)

6

Firmato int e unsigned int hanno la stessa dimensione in memoria, l'unica differenza tra loro è il modo in cui li interpretate. I valori firmati utilizzano una rappresentazione a due complementi.

Se si inserisce 0xFFFFFFFF in una posizione di memoria a 4 byte e quindi si chiede qual è il valore in là? Bene, se lo interpretiamo come int con segno, allora è -1, ma se lo interpretiamo come int unsigned il valore è 4294967295. In entrambi i casi è lo stesso schema di bit, la differenza è ciò che significa che tu gli dai.

Quando hai assegnato 10 - 20 a un int unsigned, hai calcolato un valore di -10 (C non esegue il controllo di overflow o underflow), questo è un pattern di bit di 0xFFFFFFF6, che significa -10 in un int firmato o 4294967286 in un int unsigned Se poi comunichi al compilatore (usando% i) di stampare un int firmato, interpreta quel modello di bit come int firmato e stampa -10, se hai detto al compilatore (usando% u) di stampare un int unsigned interpreta quel modello di bit come non firmato e stampa 4294967286.

+0

Quindi, il modo in cui interpreto il pattern di bit controlla il valore nella memoria. Grazie. –

+0

Bene, il valore "in memoria" è sempre lo stesso. Sono gli stessi bit. Ciò che cambia è il modo in cui viene emesso. – Veky

Problemi correlati