/*************************************************************************************************************************************/ /* */ /* T E S T L I N E A I R E , T R I V I A L E T V I O L E N T D E S E R R E U R S D ' A R R O N D I : */ /* */ /* */ /* Author of '$xtc/flottant.42$c' : */ /* */ /* Jean-Francois COLONNA (LACTAMME, 20091109092950). */ /* */ /*************************************************************************************************************************************/ #include <stdio.h> main() { double A,B,x0,x1,x2,x3,x4,x5,x6,x7; /* On notera qu'utiliser la simple precision : */ /* */ /* float A,B,x0,x1,x2,x3,x4,x5,x6,x7; */ /* */ /* donne ("malheureusement"...) un resultat parfait (x=1). Cela est un peu paradoxal car */ /* avec ce programme trivial, augmenter la precision ('float' --> 'double') donne de mauvais */ /* resultats alors qu'habituellement cela en ameliore la qualite ! */ B=4095.1; A=B+1; /* D'ou : */ /* */ /* A - B = 1 */ /* */ /* */ /* On notera qu'ecrire (de facon plus logique...) : */ /* */ /* A = 4096.1; */ /* B = A-1; */ /* */ /* donne ("malheureusement"...) un resultat parfait (x=1)... */ x0 = 1; x1 = (A*x0) - B; x2 = (A*x1) - B; x3 = (A*x2) - B; x4 = (A*x3) - B; x5 = (A*x4) - B; x6 = (A*x5) - B; x7 = (A*x6) - B; /* Evidemment : */ /* */ /* x1 = A*x0 - B */ /* = A*1 - B */ /* = A - B */ /* = 1 */ /* */ /* et de meme : */ /* */ /* x2 = x3 = x4 = x5 = x6 = x7 = 1 */ /* */ /* */ /* L'absence d'iteration ci-dessus est destinee a rendre le programme le plus simple et le */ /* plus facilement lisible possible. On evite ainsi, en particulier, l'ecriture : */ /* */ /* x = A*x - B */ /* */ /* qui ressemble trop a une equation et qui peut donc etre difficilement comprehensible */ /* pour un non programmeur... */ /* */ /* */ /* Du coup, ce programme possede deux proprietes exceptionnelles : */ /* */ /* 1-Il ne peut contenir ni d'erreurs(s) de logique, ni d'erreurs(s) de programmation ! */ /* */ /* 2-La valeur exacte des resultats {x1,x2,x3,x4,x5,x6,x7} est connue a l'avance (=1) ! */ /* */ printf("x0=%+.16f\n",x0); printf("x1=%+.16f\n",x1); printf("x2=%+.16f\n",x2); printf("x3=%+.16f\n",x3); printf("x4=%+.16f\n",x4); printf("x5=%+.16f\n",x5); printf("x6=%+.16f\n",x6); printf("x7=%+.16f\n",x7); /* Donne les resultats suivants : */ /* */ /* x0= +1.0000000000000000 */ /* x1= +1.0000000000004547 */ /* x2= +1.0000000018630999 */ /* x3= +1.0000076314440776 */ /* x4= +1.0312591580864137 */ /* x5= +129.0406374377594148 */ /* x6= +524468.2550088063580915 */ /* x7=+2148270324.2415719032287598 */ /* */ /* */ /* Le probleme vient de la partie decimale (0.1) de 4095.1 car, en effet, elle demande une */ /* infinite de "decimales" en binaire : */ /* */ /* 0.0 0011 0011 0011 0011 0011 0011 0011 0011 0011 ... (ad infinitum) */ /* */ /* et ne peut donc etre representee exactement dans un ordinateur... */ }