Représentation scientifique des nombres
En base 10
Tout nombre non-nul peut être représenté sous la forme d’une représentation scientifique, c’est-à-dire :
La décomposition se fait entre mantisse (partie de gauche) et exposant sur le 10 :
- la mantisse doit être comprise entre 1 inclus et 10 exclu, c’est-à-dire que la partie entière de la mantisse doit être constituée d’un unique chiffre non-nul ;
- l’exposant doit être un entier relatif.
En base 2
En reprenant cette idée de représentation scientifique, on obtient, pour la base 2 :
Remarquez que le chiffre à gauche de la virgule étant non-nul, il s’agit forcément de en base 2. Donc, pour stocker en mémoire n’importe quel nombre réel non-nul, il suffit de stocker la partie droite de la mantisse (le 1 étant toujours présent, il n’est pas utile de le stocker) et la puissance.
Le problème, bien sûr, est que la mantisse peut-être a priori infini, et que les exposants peuvent être très grand. Pour l’exposant, ce n’est pas forcément un très grand soucis, quelques petites astuces pouvant être utilisées pour représenter des nombres d’une taille arbitrairement grand (c’est le cas pour les entiers int en Python 3).
Les astuces pour la mantisse sont plus compliquées : au lieu de la constitution de la mantisse, il faut plutôt stocker l’algorithme permettant de calculer une mantisse de taille arbitraire. Si dans certains cas, des calculs à précision arbitraire (on parle d’arithmétique multi-précision) peuvent être intéressants, dans l’immense majorité des cas (la quasi-totalité en fait), des calculs à précision constante sont suffisants pour les calculs effectués.
L’une des principales raisons étant le principe garbage in, garbage out : il n’est pas utile de travailler sur beaucoup plus de chiffres significatifs que les chiffres significatifs des mesures : cela pourrait même pousser les utilisateurs les moins prudents à sur-estimer la précision de leur calcul.
Les représentations binaires IEEE 754 standard
Le principe de l’arithmétique de la norme IEEE 754 (prononcé I3E 754) est de tronqué la mantisse et de limiter les exposants. Pour ne pas avoir à se soucier de stocker des exposants négatifs, un décalage est présent. On a donc le format suivant pour la quasi-totalité des nombres de la norme :
1 bit est toujours utilisé pour le signe ( pour les positifs,
pour les négatifs). Le partage du reste des bits entre mantisse et exposant est synthétisé dans le tableau suivant :
Code | Nom | Bits (octets) | Taille exposant | Taille mantisse |
binary16 | Demi-précision | 16 (2) | 5 | 10 |
binary32 | Simple précision | 32 (4) | 8 | 23 |
binary64 | Précision double | 64 (8) | 11 | 52 |
binary128 | Précision quadruple | 128 (16) | 15 | 112 |
binary256 | Précision octuple | 256 (32) | 19 | 236 |
On voit que la taille de l’exposant a tendance à grandir beaucoup plus lentement que la mantisse. En effet, les utilisations de nombres très grands ou très petits est souvent rare, et on peut facilement se ramené à des nombres proches de l’unité en faisant des choix pertinents d’unités et de sous-unités si le besoin se fait ressentir. Par contre, l’augmentation de la taille de la mantisse est primordial pour augmenter la précision relative des nombres (plus de chiffres significatifs).
Le décalage de l’exposant dépend de la taille en bits de l’exposant :
Subtilités de la norme IEEE 754 : 0, nombres dénormalisés, infini et les non-nombres
2 valeurs particulières d’exposant entraine une interprétation différentes :
- Lorsque l’exposant est à 0, on se retrouve avec une exposant qui correspond à celui de 1, mais une mantisse qui commence par 0 à gauche de la virgule. Cela permet en particulier de coder le 0 lorsque la mantisse est à 0. On parle de nombres dénormalisés pour cet ensemble de nombres (0 étant exclu). Cette astuce permet de coder le 0 et d’avoir une certaine continuité plus ou moins factice entre 0 et le premier nombre normalisé.
- Lorsque l’exposant est maximum et la mantisse nul, cela représente l’infini inf.
- Lorsque l’exposant est maximum et la mantisse est non-nulle, cela représente un non-nombre : NaN, Not a Number. Si la mantisse commence par 0, cela représente un NaN avertisseur (signaling) et si elle commence par 1, cela représente un NaN silencieux (quiet). Le premier doit provoquer une erreur lors de calcul, tandis que le deuxième doit juste s’étendre : le résultat d’un calcul avec un NaN retournant un NaN (le bit précis signaliant la différence entre les deux NaN est une spécificité de la norme IEEE 754-2008).
Il est à noté que l’implémentation totale et entière de la norme n’est pas toujours respecté. Python, par exemple, retourne une erreur au lieu de l’infini lors d’une division par 0, contrairement à la recommandation de la norme.
Formule donnant la taille de l’exposant en fonction de la taille du nombre
On a des normes pour des nombres d’octets allant de 2 à 32 en doublant à chaque fois la taille. C’est assez logique en considérant les architectures des ordinateurs. Mais pour un but pédagogique, ou pour des applications très spécifiques, on peut s’inspirer de la norme IEEE-754 pour arriver à une nouvelle norme cohérente (comme les fomats minifloat).
Une formule permettant de donner la taille de l’exposant en bits en fonction de la taille du nombre en bit
est la suivante :
Cela donne 3 bits d’exposant pour un nombre de 8 bits (1 octet). Cela permet d’avoir une mantisse de 4 bits (une moitié d’octets), ce qui est plutôt intéressant (il existe des possibilités de travailler plus ou moins indépendamment sur les 2 moitiés d’un octet sur beaucoup d’architectures matérielles).
Flottant quart de précision (sur 1 octet)
Attention, tout ce qui va être discuté ensuite n’a qu’une visée pédagogique : cela sera le plus possible cohérent avec le reste de la norme, mais il ne s’agit ni d’un nom, ni d’une représentation officielle des flottants suivant la norme IEEE 754 (à ma connaissance). D’après mes recherches, elle semble être utilisée dans certains contextes (en particulier dans des situations d’informatique embarquée), mais ce n’est pas ce qui m’intéresse particulièrement dans ce billet. L’intérêt est de pouvoir représenter la totalité des nombres de la norme dans un tableau !
Décalage d’exposant
On a un exposant de taille 3, donc un décalage de . Les exposants ont des valeurs de 0 à 7, mais 0 représente les nombres dénormalisés et 7 représente l’infini et les NaN.
Nombres normalisés
Les nombres normalisés ont donc un exposant non-décalé de 1 à 6, et donc, avec le décalage de 3, les exposants sont compris entre -2 et 3. Le plus petit nombre normalisé est . Le plus grand nombre est
.
Nombres dénormalisés
Les nombres dénormalisés ont un exposant de -2. Le plus petit nombre dénormalisé strictement positif est donc : et le plus grand nombre dénormalisé est
.
Tableaux des 128 valeurs positives du format quart de précision
000 | 001 | 010 | 011 | 100 | 101 | 110 | 111 | |
0000 | 0.0 | 0.25 | 0.5 | 1.0 | 2.0 | 4.0 | 8.0 | inf |
0001 | 0,015625 | 0,265625 | 0,53125 | 1,0625 | 2,125 | 4,25 | 8,5 | sNaN |
0010 | 0,03125 | 0,28125 | 0,5625 | 1,125 | 2,25 | 4,5 | 9 | sNaN |
0011 | 0,046875 | 0,296875 | 0,59375 | 1,1875 | 2,375 | 4,75 | 9,5 | sNaN |
0100 | 0,0625 | 0,3125 | 0,625 | 1,25 | 2,5 | 5 | 10 | sNaN |
0101 | 0,078125 | 0,328125 | 0,65625 | 1,3125 | 2,625 | 5,25 | 10,5 | sNaN |
0110 | 0,09375 | 0,34375 | 0,6875 | 1,375 | 2,75 | 5,5 | 11 | sNaN |
0111 | 0,109375 | 0,359375 | 0,71875 | 1,4375 | 2,875 | 5,75 | 11,5 | sNaN |
1000 | 0,125 | 0,375 | 0,75 | 1,5 | 3 | 6 | 12 | qNaN |
1001 | 0,140625 | 0,390625 | 0,78125 | 1,5625 | 3,125 | 6,25 | 12,5 | qNaN |
1010 | 0,15625 | 0,40625 | 0,8125 | 1,625 | 3,25 | 6,5 | 13 | qNaN |
1011 | 0,171875 | 0,421875 | 0,84375 | 1,6875 | 3,375 | 6,75 | 13,5 | qNaN |
1100 | 0,1875 | 0,4375 | 0,875 | 1,75 | 3,5 | 7 | 14 | qNaN |
1101 | 0,203125 | 0,453125 | 0,90625 | 1,8125 | 3,625 | 7,25 | 14,5 | qNaN |
1110 | 0,21875 | 0,46875 | 0,9375 | 1,875 | 3,75 | 7,5 | 15 | qNaN |
1111 | 0,234375 | 0,484375 | 0,96875 | 1,9375 | 3,875 | 7,75 | 15,5 | qNaN |
Comparaison avec les flottants de Python
Pour connaitre les performances de votre systèmes concernant les flottants, vous pouvez utiliser le module sys :
>>> import sys ; sys.float_info
sys.float_info(max=1.7976931348623157e+308, max_exp=1024, max_10_exp=308,
min=2.2250738585072014e-308, min_exp=-1021, min_10_exp=-307, dig=15,
mant_dig=53, epsilon=2.220446049250313e-16, radix=2, rounds=1)
Sauf si vous avez une architecture vraiment primitive, vous devriez avoir un résultat très similaire à celui-ci :
- radix =2 confirme qu’il s’agit d’un format binaire (la norme IEEE 754 permet des représentation en base 10, ce qui n’est pas discuté dans ce billet, car très rarement utilisé et moins efficace).
- max et min représentent les extremas des valeurs normalisées. On a 15,5 et 0,25 pour le format quart de précision.
- max_exp et min_exp avec un décalage de 1 (précisé dans la documentation, mais j’avoue que je suis surpris de ce choix…), donnent les valeurs des extremas possible pour les puissances de radix : ici
et
sont représentables par des valeurs normalisés. On a 4 et -1 pour le format quart de précision (car
et
sont représentables par des valeurs normalisés).
- max_10_exp et min_10_exp correspondent aux puissances de 10 extrêmes des valeurs normalisées (sans décalage cette fois). On a 1 et -1 pour le format quart de précision.
- mant_dig correspond au nombre de chiffres significatif en base 2 pour les nombres normalisés (donc taille de la mantisse plus 1). On a 5 pour le format quart de précision.
- dig correspond au nombre de chiffre significatif en décimal. On a 1 pour le format quart de précision
- epsilon correspond à la différence entre le nombre 1 et son successeur : en pratique, c’est une borne haute de la précision relative entre 2 successeurs, et donc, en général de la précision relative des calculs. On a 0,0625 pour le format quart de précision
- round correspond au mode d’arrondi : il utilise l’arrondi au plus proche du nombre pair, ce qui est la méthode classique en informatique (j’avoue ne pas savoir pourquoi…).
Représentation graphique de la répartition et de l’erreur relative


Si on fait la même chose pour le format demi-précision, on y voit tout de suite un peu moins clair et des subtilités visibles sur un format de précision moindre passe à la trappe.

