Est-il toujours vrai que long int
(qui, autant que je sache, est synonyme de long
) est 4
octets?
Puis-je compter sur cela? Sinon, cela pourrait-il être vrai pour un système d'exploitation basé sur POSIX?
Les standards ne disent rien sur la taille exacte des types entiers mis à part char
. Généralement, long
est 32 bits sur les systèmes 32 bits et 64 bits sur les systèmes 64 bits.
La norme spécifie toutefois une taille minimum. À partir de la section 5.2.4.2.1 de la norme C :
1 Les valeurs indiquées ci-dessous doivent être remplacées par des expressions constantes utilisables dans
#if
directives de prétraitement. De plus, à l'exception deCHAR_BIT
etMB_LEN_MAX
, les éléments suivants doivent être remplacés par des expressions du même type qu’une expression qui est un objet du type correspondant converti en fonction des promotions d’entier. Leurs valeurs définies par la mise en oeuvre doivent être égales ou supérieures en magnitude (valeur absolue) à celles indiquées, avec le même signe....
valeur minimale pour un objet de type
long int
LONG_MIN
-2147483647 // - (2 ^ 31−1)valeur maximale pour un objet de type
long int
LONG_MAX
+2147483647 // 2 ^ 31−1
Ceci dit qu'un long int
must 32 bits minimum, mais peut être plus volumineux. Sur une machine où CHAR_BIT
est 8, cela donne une taille d’octet minimale de 4. Cependant, sur une machine avec par ex. CHAR_BIT
égal à 16, un long int
pourrait durer 2 octets.
Voici un exemple du monde réel. Pour le code suivant:
#include <stdio.h>
int main ()
{
printf("sizeof(long) = %zu\n", sizeof(long));
return 0;
}
Sortie sur Debian 7 i686:
sizeof (long) = 4
Sortie sur CentOS 7 x64:
sizeof (long) = 8
Donc non, vous ne pouvez faire aucune hypothèse sur la taille. Si vous avez besoin d’un type de taille spécifique, vous pouvez utiliser les types définis dans stdint.h
. Il définit les types suivants:
int8_t
: signé 8 bitsuint8_t
: non signé 8 bitsint16_t
: signé 16 bitsuint16_t
: non signé 16 bitsint32_t
: signé 32 bitsuint32_t
: non signé 32 bitsint64_t
: signé 64 bitsuint64_t
: non signé 64 bitsLe stdint.h
en-tête est décrit à la section 7.20 de la norme et les types de largeur exacts à la section 7.20.1.1. La norme indique que ces typedefs sont facultatifs, mais ils existent dans la plupart des implémentations.
Non, ni la norme C ni POSIX ne le garantissent et en fait la plupart des plates-formes 64 bits de type Unix ont un format 64 bits (8 octets) long
.
Utilisez le code sizeof(long int)
et vérifiez la taille. Cela vous donnera la taille de long int en octets sur le système sur lequel vous travaillez actuellement. La réponse à votre question est en particulier NON. Cela n’est garanti nulle part en C, en POSIX ou ailleurs.
Comme l'a souligné @delnan, les implémentations POSIX conservent la taille non spécifiée de long
et int
, qui diffère souvent entre les systèmes 32 bits et 64 bits.
La longueur de long
est principalement liée à matériel (correspondant souvent à la taille des registres de données de la CPU et parfois à d’autres problèmes logiciels, tels que la conception du système d’exploitation et l’interfaçage ABI).
Pour soulager votre esprit, sizeof
n'est pas une fonction, mais une directive de compilation *, de sorte que votre code n'utilise pas d'opérations lorsque vous utilisez sizeof
- c'est la même chose que d'écrire un nombre, mais seulement portable.
utilisation:
sizeof(long int)
* Comme Dave l'a souligné dans les commentaires, sizeof
sera calculé au moment de l'exécution lorsqu'il sera impossible de calculer la valeur lors de la compilation, par exemple lors de l'utilisation de tableaux de longueur variable.
De plus, comme indiqué dans un autre commentaire, sizeof
prend en compte le remplissage et l'alignement utilisés par l'implémentation, ce qui signifie que les octets réellement utilisés pourraient être différents de la taille en mémoire (cela pourrait être important lors du décalage de bits ).
Si vous recherchez des variables de la taille d'un octet, envisagez d'utiliser un tableau d'octets ou (je suppose supposé être pris en charge) les types définis par C99 dans stdint.h
- comme suggéré par @dbush.
Lorsque nous avons implémenté C pour la première fois le matériel ICL série 39, nous avons pris le standard au format Word et mappé les types de données sur la représentation naturelle de l'architecture de cette machine, à savoir short
= 32 bits, int
= 64 bits, long
= 128 bits.
Mais nous avons constaté qu'aucune application C sérieuse ne fonctionnait; ils ont tous assumé le mappage short
= 16, int
= 32, long
= 64, et nous avons dû changer le compilateur pour le supporter.
Ainsi, quoi que dise la norme officielle, depuis de nombreuses années tout le monde a convergé sur long
= 64 bits et il est peu probable que cela change.
Le standard ne dit rien sur la taille de long int
, il dépend donc de l’environnement que vous utilisez.
Pour obtenir la taille de long int
sur votre environnement, vous pouvez utiliser l’opérateur sizeof
et obtenir la taille de long int
. Quelque chose comme
sizeof(long int)
La norme C exige seulement les points suivants concernant les tailles de types
- int> = 16 bits,
- long> = 32 bits,
- long long (depuis C99)> = 64 bits
- sizeof (char) <= sizeof (court) <= sizeof (int) <= sizeof (long) <= sizeof (long long)
- sizeof (char) == 1
- CHAR_BIT> = 8
Le reste étant des implémentations définies, il n'est donc pas surprenant que l'on rencontre des systèmes où int a 18/24/36/60 bits, sa forme signée en complément, sizeof (char) == sizeof (short) == sizeof (int) == sizeof (long) == 4, 48 bits de long ou 9 bits tels que des architectures exotiques qui intéressent les comités de normalisation et une liste des plates-formes supportées par le standard C
Le point à propos de long int ci-dessus est complètement faux. La plupart des implémentations Linux/Unix définissent longtemps comme un type 64 bits, mais ce n’est que 32 bits dans Windows car ils utilisent des modèles de données différents (consultez le tableau ci-dessous informatique 64 bits ), et c’est indépendamment de la version 32 ou 64 bits du système d'exploitation.
Le compilateur détermine la taille en fonction du type de matériel et du système d'exploitation.
Donc, les hypothèses ne devraient pas être faites concernant la taille.
La norme la laisse complètement au compilateur, ce qui signifie également que le même compilateur peut le faire dépendre des options et de l'architecture cible.
Donc vous ne pouvez pas.
Incidemment long int
est identique à long
.
Réponse courte: non! Vous ne pouvez pas émettre d'hypothèses fixes sur la taille de long int
. En effet, le standard (standard C ou POSIX) ne documente pas la taille de long int
(Comme souligné à plusieurs reprises). Juste pour fournir un exemple contre vous, la plupart des systèmes 64 bits ont long
de taille 64! Pour maximiser la portabilité, utilisez sizeof
de manière appropriée.
Utilisez sizeof(long int)
pour vérifier la taille, il renvoie la taille de long
en octets. La valeur dépend du système ou de l'environnement. Cela signifie que le compilateur détermine la taille en fonction du matériel et du système d'exploitation.