Perché compilatore non dà errore quando valore con segno è assegnato a numero intero senza segno? - C ++
-
12-09-2019 - |
Domanda
So unsigned int non può contenere valori negativi. Ma il seguente codice viene compilato senza errori / avvisi.
unsigned int a = -10;
Quando stampo la variabile a , ottengo un valore errato stampata. Se le variabili non firmati non possono contenere valori con segno, perché i compilatori consentono loro di compilare senza dare alcun errore / avvertimento?
Qualche idea?
Modifica
Compiler: VC ++ compilatore
Soluzione
necessità di utilizzare il livello di avviso 4.
Soluzione
Microsoft Visual C ++:
C4245 avvertimento: 'inizializzazione': conversione da 'int' a 'unsigned int', firmato / unsigned mancata corrispondenza
Il livello 4 di avvertimento.
G ++
Mi dà l'avvertimento:
Attenzione: la conversione del valore negativo int
-0x00000000a' to
unsigned '
Senza le direttive -W.
GCC
È necessario utilizzare:
gcc main.c -Wconversion
che darà l'avviso:
Attenzione: negativo intero convertito in modo implicito tipo unsigned
Si noti che -Wall non permetterà questo avvertimento.
Forse avete solo bisogno di trasformare i livelli di allarme alto.
Altri suggerimenti
La conversione di un signed int
a un unsigned int
è qualcosa di noto nello standard C come una "conversione aritmetica solito", quindi non è un errore.
Il motivo compilatori spesso non emettere un avviso su questo di default è perché è così comunemente fatto in codice ci sarebbero troppi avvertimenti "falsi positivi rilasciati in generale. C'è un sacco di codice là fuori che funziona con i valori signed int
a che fare con le cose che sono intrinsecamente non firmato (calcolo delle dimensioni del buffer, per esempio). E 'anche molto comune per mescolare i valori con e senza segno nelle espressioni.
Questo non vuol dire che queste conversioni silenziosi non sono responsabili per i bug. Quindi, potrebbe non essere una cattiva idea per abilitare l'avviso per il nuovo codice in modo che sia 'pulita' fin dall'inizio. Tuttavia, credo che si sarebbe probabilmente trovare piuttosto schiacciante per affrontare gli avvertimenti emessi da codice esistente.
-10 viene analizzato come un valore intero, e assegnando int unsigned int è consentito. Per conoscere si sta facendo qualcosa di sbagliato il compilatore deve verificare se il numero intero (-10) è negativo o positivo. Dato che è più di un controllo di tipo, credo che è stato disattivato per problemi di prestazioni.
Per compilatore gcc è possibile aggiungere
gcc -Wconversion ...
E questo produrrà il seguente avviso
warning: converting negative value '-0x0000000000000000a' to 'unsigned int'
Sto usando g ++ 4.9.2 e la necessità di utilizzare -Wsign conversione per far apparire questo avviso.
gcc.gnu.org : Avvertenze circa le conversioni tra numeri interi con e senza segno sono disabilitati di default in C ++ a meno -Wsign-conversione è esplicitamente abilitato.