Une variable Integer en C occupe-t-elle 2 octets ou 4 octets?
Cela dépend de la plate-forme que vous utilisez, ainsi que de la configuration de votre compilateur. La seule réponse qui fait autorité est d'utiliser l' sizeof
opérateur pour voir la taille d'un entier dans votre situation spécifique.
De quels facteurs cela dépend-il?
La gamme pourrait être mieux considérée, plutôt que la taille . Les deux varient en pratique, bien qu'il soit beaucoup plus infaillible de choisir des types de variables par plage que par taille, comme nous le verrons. Il est également important de noter que la norme nous encourage à envisager de choisir nos types d'entiers en fonction de la plage plutôt que de la taille , mais pour l'instant ignorons la pratique standard , et laissons notre curiosité explorer sizeof
, octets et CHAR_BIT
, et représentation entière ... le terrier du lapin et le voir par nous-mêmes ...
sizeof
, octets et CHAR_BIT
La déclaration suivante, tirée de la norme C (liée à ci-dessus), décrit cela avec des mots que je ne pense pas pouvoir être améliorés.
L' sizeof
opérateur donne la taille (en octets) de son opérande, qui peut être une expression ou le nom entre parenthèses d'un type. La taille est déterminée à partir du type de l'opérande.
En supposant qu'une compréhension claire nous mènera à une discussion sur les octets . Il est communément admis qu'un octet est de huit bits, alors qu'en fait, CHAR_BIT
vous indique combien de bits il y a dans un octet . C'est juste une autre de ces nuances qui n'est pas prise en compte lorsque l'on parle des entiers communs à deux (ou quatre) octets .
Concluons les choses jusqu'à présent:
sizeof
=> taille en octets, et
CHAR_BIT
=> nombre de bits dans l'octet
Ainsi, selon votre système, sizeof (unsigned int)
peut être n'importe quelle valeur supérieure à zéro (pas seulement 2 ou 4), comme si CHAR_BIT
était 16, alors un seul octet (seize bits) contient suffisamment de bits pour représenter l'entier de seize bits décrit par le normes (citées ci-dessous). Ce n'est pas nécessairement une information utile, n'est-ce pas? Allons plus loin ...
Représentation entière
Les C norme spécifie la précision / gamme minimum pour tous les types entiers standard (et CHAR_BIT
, aussi, FWIW) ici . À partir de là, nous pouvons déduire un minimum pour le nombre de bits requis pour stocker la valeur , mais nous pouvons tout aussi bien choisir nos variables en fonction de plages . Néanmoins, une grande partie des détails requis pour cette réponse réside ici. Par exemple, ce qui suit que la norme unsigned int
nécessite (au moins) seize bits de stockage:
UINT_MAX 65535 // 2¹⁶ - 1
Ainsi, nous pouvons voir qu'il unsigned int
faut ( au moins ) 16 bits , c'est là que vous obtenez les deux octets (en supposant que CHAR_BIT
c'est 8) ... et plus tard, lorsque cette limite est passée à 2³² - 1
, les gens déclaraient 4 octets à la place. Ceci explique les phénomènes que vous avez observés:
La plupart des manuels disent que les variables entières occupent 2 octets. Mais lorsque j'exécute un programme imprimant les adresses successives d'un tableau d'entiers, il montre la différence de 4.
Vous utilisez un ancien manuel et compilateur qui vous enseigne le C non portable; l'auteur qui a écrit votre manuel pourrait même ne pas être au courant CHAR_BIT
. Vous devriez mettre à jour votre manuel (et votre compilateur) et vous efforcer de vous rappeler que l'informatique est un domaine en constante évolution sur lequel vous devez garder une longueur d'avance pour rivaliser ... Assez parlé de cela, cependant; voyons quels autres secrets non portables stockent ces octets entiers sous-jacents ...
Les bits de valeur sont ce que les idées fausses courantes semblent compter. L'exemple ci-dessus utilise un unsigned
type entier qui ne contient généralement que des bits de valeur, il est donc facile de rater le diable dans les détails.
Bits de signe ... Dans l'exemple ci-dessus, j'ai cité UINT_MAX
la limite supérieure unsigned int
car c'est un exemple trivial pour extraire la valeur 16
du commentaire. Pour les types signés, afin de faire la distinction entre les valeurs positives et négatives (c'est le signe), nous devons également inclure le bit de signe.
INT_MIN -32768 // -(2¹⁵)
INT_MAX +32767 // 2¹⁵ - 1
Bits de remplissage ... Bien qu'il soit rare de rencontrer des ordinateurs qui ont des bits de remplissage en nombres entiers, la norme C permet que cela se produise; certaines machines (c'est-à - dire celle-ci ) implémentent des types d'entiers plus grands en combinant deux valeurs entières plus petites (signées) ensemble ... et lorsque vous combinez des entiers signés, vous obtenez un bit de signe perdu. Ce bit gaspillé est considéré comme du remplissage en C. D'autres exemples de bits de remplissage peuvent inclure des bits de parité et des bits d'interruption .
Comme vous pouvez le voir, la norme semble encourager la prise en compte de plages telles que INT_MIN
.. INT_MAX
et d' autres valeurs minimales / maximales de la norme lors du choix des types d'entiers, et déconseille de s'appuyer sur les tailles car il y a d'autres facteurs subtils susceptibles d'être oubliés tels que les CHAR_BIT
bits de remplissage qui pourrait affecter la valeur de sizeof (int)
(c'est-à-dire que les idées fausses courantes sur les entiers à deux et quatre octets négligent ces détails).