Behandelt C hexadezimale Konstanten (zB 0x23FE) und signed oder unsigned int?
Vorzeichenlose Hexadezimalkonstante in C?
Amr Bekhit
Die Zahl selbst wird immer als nicht negative Zahl interpretiert. Hexadezimale Konstanten haben kein Vorzeichen oder eine inhärente Möglichkeit, eine negative Zahl auszudrücken. Der Typ der Konstante ist der erste davon, der ihren Wert darstellen kann:
int
unsigned int
long int
unsigned long int
long long int
unsigned long long int
-
Beachten Sie, dass 0x8000 folglich entweder signiert oder unsigniert sein kann, je nachdem, ob sizeof(int) 2 oder 4 ist. Yuck! Einfach anhängen
u
wenn du wirklich brauchstunsigned
.– anatolyg
19. Januar 2011 um 17:15 Uhr
-
@anatolyg: Ich bin mir nicht sicher, was du mit “igitt” meinst. Es wird immer positiv sein und es wird immer in den richtigen Wert konvertiert, wenn es einem anderen Typ zugewiesen oder befördert wird, bei dem der Wert noch im Bereich liegt, was mir wie ein ziemlich vernünftiges und wünschenswertes Verhalten erscheint.
– CB Bailey
19. Januar 2011 um 17:18 Uhr
-
@anatolyg: Aber
0x8000
ist nicht negativ. Entweder es passt in einint
in welchem Fall0x8000 > 0x7000
erfolgt als Vergleich vonint
Andernfalls0x8000
ist einunsigned
und0x7000
befördert wirdunsigned
(keine Wertänderung) und der Vergleich ist ein Vergleich vonunsigned
. Das Ergebnis stimmt jedenfalls.– CB Bailey
19. Januar 2011 um 20:35 Uhr
-
Dezimal- und Oktalkonstanten haben auch kein Vorzeichen – wenn Sie schreiben
-1
du schreibst ein Unary-
gefolgt von einer Dezimalkonstante1
. In @anatolygs Beispiel,if (MYSIZE > -1)
könnte überraschende Ergebnisse liefern, da die-1
kann zu unsigniert befördert werden oder nicht.– Café
20. Januar 2011 um 0:20 Uhr
-
@café:
0x8000 > -1
ist ein viel besseres Beispiel dafür, wo Pflege definitiv erforderlich ist.– CB Bailey
20. Januar 2011 um 7:50 Uhr
Es behandelt sie als int
Literale (im Grunde als signed int!). Um ein vorzeichenloses Literal zu schreiben, fügen Sie einfach hinzu u
Am Ende:
0x23FEu
-
Ich glaube nicht, dass man diese Aussage so stehen lassen kann. ZB vorausgesetzt, dass die Breite von
int
ist 32 Bit der Wert0x8000
istunsigned
(nämlichINT_MAX + 1
) und nichtsigned
(undINT_MIN
).– Jens Gustedt
19. Januar 2011 um 16:40 Uhr
-
@JensGustedt: Vermutlich meinst du das wenn die Breite von
int
ist 16 bisschen dann0x8000
wird seinunsigned
?– CB Bailey
19. Januar 2011 um 16:43 Uhr
-
@Charles, wahrscheinlich. Bits selber zählen war noch nie meine Stärke 🙂
– Jens Gustedt
19. Januar 2011 um 16:56 Uhr
-
@JensGustedt was du sagst ist nicht wahr. Das Hex-Literal
0x8000
ist signiert, genau wie das entsprechende Literal32768
ist unterschrieben. Was Sie sagen, ergibt keinen Sinn. Nur weil der Wert eines Literals gleich istINT_MAX + 1
für eine 16-Bit-Ganzzahl ändert nichts an der Vorzeichenbeschaffenheit ihres Typs.0x8000
ist unterschrieben. Wenn Sie unsigned wollen, müssen Sie das Literal entsprechend qualifizieren als0x8000U
.– Alex
2. April 2020 um 12:21 Uhr
-
@Alex, nein. Ein Hexadezimalwert ist
int
solange der Wert hineinpasstint
und für größere Werte ist esunsigned
dannlong
dannunsigned long
usw. Siehe Abschnitt 6.4.4.1 der C-Norm. Genau wie die akzeptierte Antwort besagt.– Jens Gustedt
2. April 2020 um 13:26 Uhr
Searene
Entsprechend cpReferenzist der Typ des hexadezimalen Literals der erste Typ in der folgenden Liste, in den der Wert passen kann.
int
unsigned int
long int
unsigned long int
long long int(since C99)
unsigned long long int(since C99)
Es kommt also darauf an, wie groß deine Zahl ist. Wenn Ihre Zahl kleiner ist als INT_MAX
dann ist es vom Typ int
. Wenn Ihre Zahl größer ist als INT_MAX
aber kleiner als UINT_MAX
es ist vom Typ unsigned int
und so weiter.
Seit 0x23FE
ist kleiner als INT_MAX
(welches ist 0x7FFF
oder höher), ist es vom Typ int
.
Wenn Sie möchten, dass es unsigniert ist, fügen Sie a hinzu u
am Ende der Nummer: 0x23FEu
.
-
Diese Antwort scheint sich auf C++ und nicht auf C zu beziehen. Sie mag richtig sein, aber ich denke, der Referenzlink sollte aktualisiert werden, um auf die C-Referenz und nicht auf die C++-Referenz zu verweisen.
– Radon Rosborough
13. September 2018 um 0:25 Uhr
-
@RadonRosborough Ich habe die Antwort aktualisiert, um die C-Referenz zu verwenden, und die anderen Teile davon überprüft, um sicherzustellen, dass sich die Antwort ausschließlich auf C bezieht. Danke für den Hinweis.
– Searene
13. September 2018 um 0:49 Uhr
Mögliches Duplikat von Type of integer literals not int by default?
– phuklv
13. September 2018 um 2:09 Uhr