J'ai lu qu'ils sont stockés sous forme de mantisse et d'exposant
J'ai lu ce document mais je n'ai rien compris.
Pour comprendre comment ils sont stockés, vous devez d’abord comprendre ce qu’ils sont et le type de valeurs qu’ils sont censés gérer.
Contrairement aux nombres entiers, une valeur en virgule flottante est censée représenter des valeurs extrêmement petites et extrêmement grandes. Pour les valeurs à virgule flottante 32 bits normales, cela correspond à des valeurs comprises entre 1.175494351 * 10 ^ -38 à 3.40282347 * 10 ^ + 38.
Clairement, en utilisant seulement 32 bits, il n'est pas possible de stocker tous les chiffres dans de tels nombres.
En ce qui concerne la représentation, vous pouvez voir tous les nombres normaux à virgule flottante sous forme de valeurs comprises entre 1,0 et (presque) 2,0, mis à l'échelle avec une puissance de deux. Donc 1.0 est, tout simplement 1,0 * 2 ^ 0. 2.0 est 1,0 * 2 ^ 1. -5.0 est -1,25 * 2 ^ 2.
Alors, que faut-il pour encoder cela le plus efficacement possible? De quoi avons-nous vraiment besoin?
Ceci est codé comme suit, conformément à la norme à virgule flottante IEEE-754.
Outre les valeurs à virgule flottante normales, il existe un certain nombre de valeurs spéciales:
Enfin, voici quelques exemples concrets (toutes les valeurs sont en hex):
En termes simples, il s'agit essentiellement de notation scientifique en binaire. La norme officielle (avec les détails) est IEEE 754 .
typedef struct {
unsigned int mantissa_low:32;
unsigned int mantissa_high:20;
unsigned int exponent:11;
unsigned int sign:1;
} tDoubleStruct;
double a = 1.2;
tDoubleStruct* b = reinterpret_cast<tDoubleStruct*>(&a);
Voici un exemple de configuration de la mémoire si le compilateur utilise la double précision IEEE 754, qui est la valeur par défaut pour un double C sur la plupart des systèmes actuels.
Le voici sous forme binaire en C et mieux lu wikipedia sur la double précision pour le comprendre.
J'ai aimé l'explication donnée dans le lien ci-dessous. De plus, la section "Sujets que vous aimerez" pointe vers des réponses à d'autres requêtes similaires.
Partage pour les enregistrements au cas où un débutant cherche l'information.
https://www.log2base2.com/storage/how-float-values-are-stored-in-memory.html
Il existe différents formats en virgule flottante. La plupart d'entre eux partagent quelques caractéristiques communes: un bit de signe, des bits dédiés au stockage d'un exposant et des bits dédiés au stockage du significande (également appelé mantisse).
La norme à virgule flottante IEEE tente de définir un format unique (ou plutôt un ensemble de formats de quelques tailles) pouvant être implémenté sur divers systèmes. Il définit également les opérations disponibles et leur sémantique. Cela fonctionne très bien et la plupart des systèmes que vous rencontrerez probablement utilisent une virgule flottante IEEE. Mais d'autres formats sont toujours utilisés, ainsi que des implémentations IEEE pas assez complètes. La norme C fournit facultatif la prise en charge de IEEE, mais ne l’oblige pas.
La mantisse représente les bits les plus significatifs du nombre.
L'exposant représente le nombre de décalages à effectuer sur la mantisse afin d'obtenir la valeur réelle du nombre.
L'encodage spécifie comment sont représentés le signe de la mantisse et le signe de l'exposant (en se déplaçant essentiellement vers la gauche ou vers la droite).
Le document auquel vous faites référence spécifie le codage IEEE, le plus utilisé.
J'ai trouvé l'article que vous avez cité assez illisible (et je connais un peu le fonctionnement des flotteurs IEEE). Je vous suggère d'essayer avec la version Wiki de l'explication. C'est assez clair et a plusieurs exemples:
http://en.wikipedia.org/wiki/Single_precision et http://en.wikipedia.org/wiki/Double_precision
C'est la mise en œuvre définie, bien que IEEE-754 soit de loin le plus courant.
Pour être sûr que IEEE-754 est utilisé:
#ifdef __STDC_IEC_559__
std::numeric_limits<float>::is_iec559