Aller au contenu

Partie 3 : Représentation des nombres réels (flottants)


Les entiers se représentent de manière exacte en binaire. Mais les nombres à virgule posent un problème fondamental : il est impossible de représenter tous les nombres réels avec un nombre fini de bits.

En effet, entre deux nombres réels quelconques, il existe une infinité d'autres nombres réels. Avec un nombre fini de bits, on ne peut coder qu'un nombre fini de valeurs. La représentation sera donc forcément approximative dans la plupart des cas.


En mathématiques et en sciences, on utilise la notation scientifique pour écrire les très grands ou très petits nombres. Le principe est de séparer le nombre en deux parties :

  • Un nombre compris entre 1 et 10 appelé la mantisse ;
  • Une puissance de 10 appelée l'exposant.
NombreNotation scientifiqueMantisseExposant
3 7503,75 × 10³3,753
0,00424,2 × 10⁻³4,2-3
602 200 000 000 000 000 000 0006,022 × 10²³6,02223

La virgule « flotte » en se déplaçant grâce à l'exposant : c'est l'origine du terme nombre flottant ou virgule flottante.


Dans un ordinateur, le même principe est appliqué, mais en base 2. Un nombre flottant est stocké sous la forme :

signe × mantisse × 2^exposant^

L'ordinateur mémorise trois informations dans un nombre fixe de bits :

ComposanteRôle
Signe1 bit : 0 pour positif, 1 pour négatif
ExposantDétermine l'ordre de grandeur (la position de la virgule)
MantisseLes chiffres significatifs du nombre

Tout comme on peut écrire des nombres à virgule en base 10, on peut le faire en base 2. Les positions après la virgule correspondent aux puissances négatives de 2 :

Position...2¹2⁰,2⁻¹2⁻²2⁻³2⁻⁴...
Valeur...21,0,50,250,1250,0625...

Méthode systématique : multiplications successives par 2

Section intitulée « Méthode systématique : multiplications successives par 2 »

Pour convertir la partie décimale d'un nombre en binaire, on peut aussi procéder par multiplications successives par 2 en ne gardant que la partie entière à chaque étape :


Puisque la mantisse a un nombre fini de bits, les nombres qui ont une représentation binaire infinie sont tronqués. Cette troncature provoque des erreurs d'arrondi.

>>> 0.1 + 0.2
0.30000000000000004
>>> 0.1 + 0.2 == 0.3
False

Ce résultat surprenant n'est pas un bug de Python. C'est une conséquence directe du fait que ni 0,1, ni 0,2, ni 0,3 ne peuvent être représentés exactement en binaire. Les petites erreurs d'arrondi s'accumulent.

>>> 0.1 + 0.1 + 0.1
0.30000000000000004
>>> 1/3
0.3333333333333333
>>> 1/3 + 1/3 + 1/3
1.0 # ici, Python compense l'erreur
>>> 0.1 * 3
0.30000000000000004
>>> 0.1 * 10
1.0000000000000002

Les erreurs d'arrondi sont infimes pour un seul calcul, mais elles peuvent s'accumuler au fil de nombreuses opérations :

>>> somme = 0.0
>>> for i in range(1000):
... somme += 0.001
>>> somme
0.9999999999999062 # au lieu de 1.0

Après 1 000 additions de 0,001, le résultat n'est pas exactement 1.



Un nombre décimal est représentable exactement en binaire si et seulement si il peut s'écrire sous la forme d'une fraction dont le dénominateur est une puissance de 2.

NombreFractionDénominateur est une puissance de 2 ?Exact en binaire ?
0,51/2Oui (2¹) Oui
0,251/4Oui (2²) Oui
0,753/4Oui (2²) Oui
0,1251/8Oui (2³) Oui
0,11/10Non (10 = 2 × 5) Non
0,21/5Non (5 n'est pas une puissance de 2) Non
0,33/10Non Non
1/31/3Non Non

ConceptDétail
Nombre flottantReprésentation approximative d'un nombre réel sous la forme signe × mantisse × 2^exposant^
Erreurs d'arrondi0,1 + 0,2 ≠ 0,3 en machine : conséquence de la représentation binaire finie
ExactitudeSeules les fractions dont le dénominateur est une puissance de 2 sont exactes
Règle fondamentaleNe jamais tester l'égalité de deux flottants avec ==
AlternativeUtiliser une marge de tolérance : abs(a - b) < epsilon
Bonne pratiquePréférer les entiers quand c'est possible (centimes au lieu d'euros)