La norme IEEE754 est utilisée pour gérer les nombres à virgules dans la plupart des langage de programmation. Ses limitations génèrent des bugs lors des calculs et du stockage en mémoire de ces nombres. Cette présentation explique les raisons de ces bugs et comment s'en prémunir. Les exemples sont donnés en javascript mais directement transposables dans d'autres langages : java, c, python...
Cette version 1.1 est abrégée par-rapport à la version 1.0.
Version pdf allégée (8 Mo) de la présentation donnée au humantalks à Laval.
Pour comprendre ce que Barbie vient faire dans ces slides : http://www.clubic.com/mag/culture/actualite-740293-barbie-coder-internet-coup-main.html
2. Shaker technologies Javascript-IEEE754 version 1.1
Human talker
Mickaël Ruau :
!
• consultant en qualité logicielle
(forges logicielles)
• spécialiste de l’informatique
médicale (norme DICOM)
• formateur à l’AFPA d’Angers
3. Shaker technologies Javascript-IEEE754 version 1.1
Références
http://blog.oaxoa.com/2008/03/22/weird-math-aka-ieee-754-
double-precision-floating-point-number-sukcs/
!
http://grouper.ieee.org/groups/754/faq.html
http://www.haypocalc.com/wiki/Standards_IEEE_754_et_854
!
http://floating-point-gui.de/languages/javascript/
http://www.ecmascript.org/
Standard ECMA-262 3rd Edition - December 1999
ECMA-262 5.1 Edition - June 2011
4. Shaker technologies Javascript-IEEE754 version 1.1
Disclaimer
Le but est de sensibiliser
aux problèmes liés aux
calculs informatiques,
notamment en matière
financière (comptabilité,
paie, ecommerce...).
!
Je ne suis pas
mathématicien.
Je n’ai pas écrit la norme
IEEE754, je ne la
connais pas par coeur!
15. Shaker technologies Javascript-IEEE754 version 1.1
La cancellation
http://fr.wikipedia.org/wiki/Virgule_flottante#Pr.C3.A9cautions_d.27emploi
Les calculs en virgule flottante (...) présentent divers
désagréments, notamment leur précision limitée, qui se
traduit par des arrondis. (...)
!
En particulier, la soustraction de deux nombres très
proches provoque une grande perte de précision relative :
on parle de « cancellation ».
16. Shaker technologies Javascript-IEEE754 version 1.1
Pourquoi 0.1 n’est pas 0.1?
http://www.haypocalc.com/wiki/Standards_IEEE_754_et_854
En gros, on stocke les nombres sous la forme :
(signe, mantisse, exposant)
ce qui donne x = signe * mantisse * (2 ^ exposant).
!
Le signe vaut +1 ou -1, la mantisse est un nombre réel
tel que 1.0 <= mantisse < 2.0,
et l'exposant est une valeur entière.
Bien sûr, l'ensemble est codé en binaire !
17. Shaker technologies Javascript-IEEE754 version 1.1
Exemples de format de stockage
!
▪ Le nombre 2 est stocké (+1, 1, 1),
c'est-à-dire : 2 = (+1) * 1 * (2 ^ 1).
▪ Le nombre 3 est stocké (+1, 1.5, 1) :
3 = (+1) * 1.5 * (2 ^ 1).
▪ Le nombre 10 est stocké (+1, 1.25, 3) :
10 = (+1) * 1.25 * 2^3.
19. Shaker technologies Javascript-IEEE754 version 1.1
Passé les bornes, y’a plus de limite!
console.log(1.00000000000000009);// affiche 1
!
var n1 = 123456789012345672;
console.log(n1); // affiche 123456789012345660
!
var n2 = 123456789012345673;
console.log(n2); // affiche 123456789012345680
21. Shaker technologies Javascript-IEEE754 version 1.1
" Il faut une infinie patience pour attendre toujours ce
qui n'arrive jamais. " (PIERRE DAC)
console.log(9999999999999999999999999999999999999
99999999999999999999999999999999999999999999999
99999999999999999999999999999999999999999999999
99999999999999999999999999999999999999999999999
99999999999999999999999999999999999999999999999
99999999999999999999999999999999999999999999999
9999999999999999999999999999999999999);
//affiche Infinity
22. Shaker technologies Javascript-IEEE754 version 1.1
" Il faut toujours prendre le maximum de risques avec
le maximum de précautions. " Rudyard Kipling
console.log(3+999999999999999);
//affiche 1000000000000002
!
console.log(3+9999999999999999);
//affiche 1000000000000004
!
console.log(3+99999999999999999);
//affiche 100000000000000000
!
console.log(2+99999999999999999);
//affiche 100000000000000000
24. Shaker technologies Javascript-IEEE754 version 1.1
IEEE 754 overflow
http://fr.wikipedia.org/wiki/Virgule_flottante
La plage d'exposants est limitée :
• « overflows » lorsque le résultat d'une opération est plus
grand que la plus grande valeur représentable
• « underflows » lorsqu'un résultat est plus petit, en valeur
absolue, que le plus petit flottant normalisé positif
• puis des résultats n'ayant plus aucun sens.
26. Shaker technologies Javascript-IEEE754 version 1.1
Number() = IEEE 64 bit
JavaScript is dynamically typed and will often convert
implicitly between strings and floating-point numbers (which
are IEEE 64 bit values).
To force a variable to floating-point, use the global
parseFloat() function.
!
var num = parseFloat("3.5");
27. Shaker technologies Javascript-IEEE754 version 1.1
https://github.com/dtrebbien/BigDecimal.js
Decimal Types
The best decimal type for JavaScript seems to be a port of
Java’s BigDecimal class, which also supports rounding
modes:
var a = new BigDecimal("0.01");
var b = new BigDecimal("0.02");
var c = a.add(b); // 0.03
var d = c.setScale(1, BigDecimal.prototype.ROUND_HALF_UP);
30. Shaker technologies Javascript-IEEE754 version 1.1
@HeforShe
Dedicated to
Pauline,
Stéphanie,
Sylvie,
Mum…
!
With love and kisses.
You girls rock in IT!
!
Credits :
Photo : http://violasong.com/2010/03/what-a-computer-engineer-looks-like
!
https://computer-engineer-barbie.herokuapp.com
Cette présentation constitue une parodie au sens de l’article L.122-5
du Code de la Propriété Intellectuelle.
This non-commercial transformative work constitutes fair use
under Section 107 of the U.S. copyright act.
Use of copyrighted material is necessary
for the purpose of criticism and education, the images are only
at the resolution necessary for this purpose,
and this remix is clearly marked to avoid confusion with the original.