Besetzt eine Integer-Variable in C 2 Bytes oder 4 Bytes? Von welchen Faktoren hängt es ab?
Die meisten Lehrbücher sagen, dass ganzzahlige Variablen 2 Bytes belegen. Wenn ich jedoch ein Programm ausführe, das die aufeinanderfolgenden Adressen eines Arrays von Ganzzahlen druckt, wird der Unterschied von 4 angezeigt.
int
ist nur einer von mehreren ganzzahligen Typen. Sie haben nach der Größe der "Ganzzahl" gefragt. Sie wollten wahrscheinlich nach der Größe von fragenint
.int
2 Bytes ist (a) bezieht sich wahrscheinlich auf ein altes System, und (b) macht nicht deutlich, dass die Größe von System zu System unterschiedlich sein wird. Das beste Buch über C ist "The C Programming Language" von Kernighan und Ritchie, obwohl es einige Programmiererfahrung voraussetzt. Siehe auch 18.10 der Frage comp.lang.c FAQ .#define int int64_t
auf einer 64-Bit-Plattform, also auch nicht. Einfach benutzensizeof
. ;-)Antworten:
Ich weiß, dass es gleich ist
sizeof(int)
. Die Größe einesint
ist wirklich compilerabhängig. Früher, als Prozessoren 16 Bit waren, warenint
es 2 Bytes. Heutzutage sind es meistens 4 Bytes auf 32-Bit- und 64-Bit-Systemen.Immer noch mit
sizeof(int)
ist jedoch der beste Weg, um die Größe einer Ganzzahl für das spezifische System zu ermitteln, auf dem das Programm ausgeführt wird.BEARBEITEN: Falsche Anweisung
int
behoben, die auf den meisten 64-Bit-Systemen 8 Byte beträgt. Zum Beispiel sind es 4 Bytes bei 64-Bit-GCC.quelle
sizeof(int)
kann ein beliebiger Wert von sein1
. Ein Byte muss nicht 8 Bit groß sein, und einige Maschinen haben keine 8-Bit-adressierbare Einheit (was im Standard die Definition eines Bytes im Standard ist). Die Antwort ist ohne weitere Informationen nicht korrekt.Dies ist einer der Punkte in C, die zunächst verwirrend sein können, aber der C-Standard gibt nur einen Mindestbereich für Ganzzahltypen an, der garantiert unterstützt wird.
int
ist garantiert in der Lage, -32767 bis 32767 zu halten, was 16 Bit erfordert. In diesem Fallint
sind es 2 Bytes. Implementierungen können jedoch über dieses Minimum hinausgehen, da Sie sehen werden, dass viele moderne Compilerint
32-Bit erstellen (was auch 4 Bytes ziemlich allgegenwärtig bedeutet).Der Grund, warum Ihr Buch 2 Bytes sagt, ist höchstwahrscheinlich, weil es alt ist. Zu einer Zeit war dies die Norm. Im Allgemeinen sollten Sie den
sizeof
Operator immer verwenden , wenn Sie herausfinden möchten, wie viele Bytes sich auf der von Ihnen verwendeten Plattform befinden.Um dies zu beheben, hat C99 neue Typen hinzugefügt, bei denen Sie explizit nach einer bestimmten Ganzzahl fragen können, z. B.
int16_t
oderint32_t
. Zuvor gab es keine universelle Möglichkeit, eine Ganzzahl mit einer bestimmten Breite zu erhalten (obwohl die meisten Plattformen ähnliche Typen pro Plattform bereitstellten).quelle
int
. C macht diese Annahme nicht. Die Komplement- und Vorzeichengrößen-Systeme von 1 können nicht-32768
in 16 Bit dargestellt werden. Vielmehr haben sie zwei Darstellungen für Null (positiv und negativ). Deshalb beträgt der Mindestbereich für eineint
ist[-32767..32767]
.Es gibt keine spezifische Antwort. Das hängt von der Plattform ab. Es ist implementierungsdefiniert. Es kann 2, 4 oder etwas anderes sein.
Die Idee dahinter
int
war, dass es der natürlichen "Wort" -Größe auf der gegebenen Plattform entsprechen sollte: 16 Bit auf 16-Bit-Plattformen, 32 Bit auf 32-Bit-Plattformen, 64 Bit auf 64-Bit-Plattformen. Aus Gründen der Abwärtskompatibilität bevorzugen einige Compiler jedoch die 32-Bit-Version,int
selbst auf 64-Bit-Plattformen.Die Zeit von 2 Byte
int
ist jedoch längst vorbei (16-Bit-Plattformen?), Es sei denn, Sie verwenden eine eingebettete Plattform mit 16-Bit-Wortgröße. Ihre Lehrbücher sind wahrscheinlich sehr alt.quelle
The idea behind int was that it was supposed to match the natural "word" size on the given platform
- Das habe ich gesucht. Irgendeine Idee, was der Grund sein könnte? In einer freien Welt könnte int eine beliebige Anzahl aufeinanderfolgender Bytes im Speicher belegen, oder? 8, 16 was auch immerDie Antwort auf diese Frage hängt davon ab, welche Plattform Sie verwenden.
Unabhängig von der Plattform können Sie jedoch zuverlässig die folgenden Typen annehmen:
quelle
Dies hängt von der verwendeten Plattform und der Konfiguration Ihres Compilers ab. Die einzig maßgebliche Antwort besteht darin, mithilfe des
sizeof
Operators zu ermitteln, wie groß eine Ganzzahl in Ihrer spezifischen Situation ist.Die Reichweite sollte am besten berücksichtigt werden, anstatt die Größe . Beide variieren in der Praxis, obwohl es viel narrensicherer ist, Variablentypen nach Bereich als Größe auszuwählen, wie wir sehen werden. Es ist auch wichtig anzumerken, dass der Standard uns dazu ermutigt, die Auswahl unserer Ganzzahltypen eher nach Bereich als nach Größe in Betracht zu ziehen. Lassen Sie uns jedoch zunächst die Standardpraxis ignorieren und unsere Neugierde untersuchen
sizeof
, BytesCHAR_BIT
und Ganzzahldarstellung untersuchen das Kaninchenloch und sehen Sie es selbst ...sizeof
, Bytes undCHAR_BIT
Die folgende Aussage aus dem C-Standard (oben verlinkt) beschreibt dies in Worten, von denen ich glaube, dass sie nicht verbessert werden können.
Die Annahme eines klaren Verständnisses führt uns zu einer Diskussion über Bytes . Es wird allgemein angenommen, dass ein Byte aus acht Bits besteht, obwohl tatsächlich angegeben
CHAR_BIT
wird, wie viele Bits in einem Byte enthalten sind . Dies ist nur eine weitere dieser Nuancen, die bei der Betrachtung der gemeinsamen Zwei- (oder Vier-) Byte-Ganzzahlen nicht berücksichtigt wird .Lassen Sie uns die Dinge so weit zusammenfassen:
sizeof
=> Größe in Bytes undCHAR_BIT
=> Anzahl der Bits im ByteJe nach System kann
sizeof (unsigned int)
also jeder Wert größer als Null sein (nicht nur 2 oder 4), als wäre erCHAR_BIT
16, dann enthält ein einzelnes (16-Bit-) Byte genügend Bits, um die durch die beschriebene 16-Bit-Ganzzahl darzustellen Standards (unten angegeben). Das sind nicht unbedingt nützliche Informationen, oder? Lassen Sie uns tiefer eintauchen ...Ganzzahlige Darstellung
Der C-Standard gibt hier die Mindestgenauigkeit / den Mindestbereich für alle Standard-Integer-Typen (und
CHAR_BIT
auch fwiw) an . Daraus können wir ein Minimum ableiten, wie viele Bits zum Speichern des Werts erforderlich sind , aber wir können unsere Variablen auch einfach basierend auf Bereichen auswählen . Dennoch befindet sich hier ein großer Teil der für diese Antwort erforderlichen Details. Zum Beispiel Folgendes, dass der Standardunsigned int
(mindestens) 16 Bit Speicher benötigt:Somit können wir sehen,
unsigned int
dass ( mindestens ) 16 Bit erforderlich sind. Hier erhalten Sie die zwei Bytes (unter der Annahme vonCHAR_BIT
8) ... und später, als diese Grenze auf erhöht wurde2³² - 1
, gaben die Leute stattdessen 4 Bytes an. Dies erklärt die Phänomene, die Sie beobachtet haben:Sie verwenden ein altes Lehrbuch und einen Compiler, die Ihnen nicht tragbares C beibringen. Der Autor, der Ihr Lehrbuch geschrieben hat, weiß es vielleicht gar nicht
CHAR_BIT
. Sie sollten Ihr Lehrbuch (und Ihren Compiler) aktualisieren und sich daran erinnern, dass die IT ein sich ständig weiterentwickelndes Feld ist, dem Sie im Wettbewerb immer einen Schritt voraus sein müssen ... Genug davon; Mal sehen, welche anderen nicht portablen Geheimnisse die zugrunde liegenden Integer-Bytes speichern ...Wertbits sind das, was die häufigsten Missverständnisse zu zählen scheinen. Im obigen Beispiel wird ein
unsigned
ganzzahliger Typ verwendet, der normalerweise nur Wertbits enthält, sodass der Teufel im Detail leicht übersehen werden kann.Vorzeichenbits ... Im obigen Beispiel habe ich
UINT_MAX
als Obergrenze angegeben,unsigned int
da dies ein triviales Beispiel ist, um den Wert16
aus dem Kommentar zu extrahieren . Bei vorzeichenbehafteten Typen müssen wir auch das Vorzeichenbit einschließen, um zwischen positiven und negativen Werten zu unterscheiden (das ist das Vorzeichen).Auffüllen von Bits ... Während es nicht üblich ist, auf Computer zu stoßen, die Auffüllbits in ganzen Zahlen enthalten, lässt der C-Standard dies zu. Einige Maschinen (dh diese ) implementieren größere Ganzzahltypen, indem sie zwei kleinere (vorzeichenbehaftete) Ganzzahlwerte miteinander kombinieren. Wenn Sie vorzeichenbehaftete Ganzzahlen kombinieren, erhalten Sie ein verschwendetes Vorzeichenbit. Dieses verschwendete Bit wird in C als Auffüllen betrachtet . Andere Beispiele für Auffüllen von Bits können Paritätsbits und Trap-Bits umfassen .
Wie Sie sehen können, scheint der Standard die Berücksichtigung von Bereichen wie
INT_MIN
..INT_MAX
und anderen Minimal- / Maximalwerten aus dem Standard bei der Auswahl von Ganzzahltypen zu fördern , und rät davon ab, sich auf Größen zu verlassen, da andere subtile Faktoren wahrscheinlich vergessen werden, wie z. B.CHAR_BIT
und Auffüllen von Bits, die Dies kann sich auf den Wert von auswirkensizeof (int)
(dh die häufigen Missverständnisse von Zwei-Byte- und Vier-Byte-Ganzzahlen vernachlässigen diese Details).quelle
C99 N1256 Standardentwurf
http://www.open-std.org/JTC1/SC22/WG14/www/docs/n1256.pdf
Die Größe
int
und alle anderen Integer-Typen sind implementierungsdefiniert. C99 gibt nur Folgendes an:5.2.4.2.1 "Größen von ganzzahligen Typen
<limits.h>
" gibt die Mindestgrößen an:6.2.5 "Typen" sagt dann:
und 6.3.1.1 "Boolescher Wert, Zeichen und Ganzzahlen" bestimmt die relativen Konvertierungsränge:
quelle
Die einzigen Garantien , dass
char
sein müssen mindestens 8 Bit Breite,short
undint
sein müssen , mindestens 16 Bit breit, undlong
sein müssen , mindestens 32 Bit breit, und dassizeof (char)
<=sizeof (short)
<=sizeof (int)
<=sizeof (long)
(gleiches gilt für die unsigned Versionen dieser Typen ).int
kann je nach Plattform zwischen 16 und 64 Bit breit sein.quelle
Die Antwort lautet "Ja" / "Nein" / "Vielleicht" / "Vielleicht nicht".
Die Programmiersprache C gibt Folgendes an: Die kleinste adressierbare Einheit, die unter "Byte" bekannt ist
char
und auch als "Byte" bezeichnet wird , ist genauCHAR_BIT
bitbreit, wobei sieCHAR_BIT
mindestens 8 beträgt.Ein Byte in C ist also nicht unbedingt ein Oktett , dh 8 Bits. In der Vergangenheit hatte eine der ersten Plattformen, auf denen C-Code (und Unix) ausgeführt wurde, 4 Byte
int
- aber insgesamtint
36 Bit, weilCHAR_BIT
es 9 war!int
soll die natürliche Ganzzahlgröße für die Plattform sein, die eine Reichweite von mindestens hat-32767 ... 32767
. Sie können die Größeint
der Plattformbytes mit abrufensizeof(int)
; Wenn Sie diesen Wert mit multiplizierenCHAR_BIT
, wissen Sie, wie breit er in Bits ist.Während 36-Bit-Maschinen größtenteils tot sind, gibt es immer noch Plattformen mit Nicht-8-Bit-Bytes. Erst gestern gab es eine Frage zu einer Texas Instruments MCU mit 16-Bit-Bytes , die einen C99, C11-kompatiblen Compiler hat.
Auf TMS320C28x scheint es , dass
char
,short
undint
sind alle 16 Bit breit, und damit ein Byte.long int
ist 2 Bytes undlong long int
ist 4 Bytes. Das Schöne an C ist, dass man für eine Plattform wie diese immer noch ein effizientes Programm schreiben und es sogar tragbar machen kann!quelle
Meistens hängt es von der Plattform ab, die Sie verwenden. Es hängt von Compiler zu Compiler ab. Heutzutage besteht int in den meisten Compilern aus 4 Bytes . Wenn Sie überprüfen möchten, was Ihr Compiler verwendet, können Sie verwenden
sizeof(int)
.Das einzige, was der Compiler verspricht, ist, dass die Größe von short gleich oder kleiner als int und die Größe von long gleich oder größer als int sein muss. Wenn also die Größe von int 4 ist, kann die Größe von short 2 oder 4 sein, aber nicht größer als das. Gleiches gilt für long und int. Es heißt auch, dass die Größe von kurz und lang nicht gleich sein kann.
quelle
%d
für einensize_t
Parameter ist UB.Dies hängt von der Implementierung ab, aber normalerweise benötigen x86 und andere gängige Architekturen wie ARMs
int
4 Byte. Sie können jederzeit zur Kompilierungszeit mitsizeof(int)
oder einem anderen Typ prüfen, den Sie überprüfen möchten.Wenn Sie sicherstellen möchten, dass Sie einen Typ einer bestimmten Größe verwenden, verwenden Sie die Typen in
<stdint.h>
quelle
Dies gibt 4 zurück, ist aber wahrscheinlich maschinenabhängig.
quelle
C erlaubt, dass "Bytes" etwas anderes als 8 Bits pro "Byte" sind.
Ein Wert von etwas mehr als 8 wird immer seltener. Verwenden Sie für maximale Portabilität
CHAR_BIT
anstelle von 8. Die Größe einesint
In- Bits in C istsizeof(int) * CHAR_BIT
.Die
int
Bitgröße beträgt üblicherweise 32 oder 16 Bit. C festgelegten Mindestbereiche :Der Mindestbereich für
int
erzwingt eine Bitgröße von mindestens 16 - selbst wenn der Prozessor "8-Bit" war. Eine Größe wie 64 Bit wird in spezialisierten Prozessoren gesehen. Andere Werte wie 18, 24, 36 usw. sind auf historischen Plattformen aufgetreten oder zumindest theoretisch möglich. Moderne Codierung macht sich selten Sorgen über Bitgrößen ohne Potenz von 2int
.Der Prozessor und die Architektur des Computers steuern die
int
Auswahl der Bitgröße.Selbst bei 64-Bit-Prozessoren kann die Compilergröße
int
aus Kompatibilitätsgründenint
32-Bit betragen, da große Codebasen von 32-Bit (oder 32/16) abhängen.quelle
Dies ist eine gute Quelle für die Beantwortung dieser Frage.
Aber diese Frage ist eine Art immer wahrheitsgemäße Antwort: "Ja. Beides."
Das hängt von Ihrer Architektur ab. Wenn Sie auf einem 16-Bit-Computer oder weniger arbeiten, darf dies nicht 4 Byte (= 32 Bit) sein. Wenn Sie auf einem 32-Bit-Computer oder einem besseren Computer arbeiten, beträgt dessen Länge 32-Bit.
Um dies herauszufinden, bereiten Sie Ihr Programm darauf vor, etwas Lesbares auszugeben, und verwenden Sie die Funktion "sizeof". Dies gibt die Größe Ihres deklarierten Datentyps in Byte zurück. Aber seien Sie vorsichtig, wenn Sie dies mit Arrays verwenden.
Wenn Sie deklarieren
int t[12];
, wird 12 * 4 Byte zurückgegeben. Verwenden Sie einfach, um die Länge dieses Arrays zu ermittelnsizeof(t)/sizeof(t[0])
. Wenn Sie eine Funktion aufbauen möchten, die die Größe eines Sendearrays berechnen soll, denken Sie daran, dass ifDas wird also nicht einmal etwas anderes zurückgeben. Wenn Sie ein Array definieren und anschließend versuchen, die Länge zu ermitteln, verwenden Sie sizeof. Wenn Sie ein Array an eine Funktion senden, denken Sie daran, dass der Sendewert nur ein Zeiger auf das erste Element ist. Aber im ersten Fall wissen Sie immer, welche Größe Ihr Array hat. Fall zwei kann herausgefunden werden, indem zwei Funktionen definiert werden und eine gewisse Leistung fehlt. Definieren Sie die Funktion (Array t) und definieren Sie die Funktion2 (Array t, int size_of_t). Rufen Sie "function (t)" auf, messen Sie die Länge durch Kopieren und senden Sie das Ergebnis an function2, wo Sie für variable Arraygrößen alles tun können, was Sie wollen.
quelle
char
immersigned
)