Logo du forum
 

Forum TT-Hardware

| Inscription | | Recherche | | FAQ | | Accueil | | Liste des membres |
| Calendrier |
 
Vous n'êtes pas identifié! [Connexion] ou [Inscription] Forum » Programmation » [C / C++ / C#] » drôle de comportement...
Login Mot de passe

1 visiteurs sur ce topic (0 membre(s), 1 invité(s) )


Auteur
Sujet : drôle de comportement...
Black_Knight
Membre hyperactif
Membre # 7740

 Avatar du membre
Lieu : Cornwall, Ontario, Canada

Messages :
234 (0.11 par jour)


Score :

Message du 23-06-2006 @ 8:09      Afficher le profil   Envoyer un message privé   Editer le message   Citer le message      Afficher l'adresse IP   Alerter les modérateurs   


bonjour.

Je débute la programmation en C, et j'ai fait un petit programme de conversion celsius <--> farhneit (comment on écrit ça!??!!)

le voila:

Code :

#include <stdio.h>

main()
{
   float fahr, celsius;
   float lower, upper, step;
   FILE* fichier = NULL;   

   fichier = fopen("conversion.txt", "w");
   lower = 0;
   upper = 300;
   step = 0.01;
   
   celsius = lower;
   while (celsius <= upper) {
      fahr = ( celsius / 5 * 9 ) + 32;
      printf("%ft%fn", celsius, fahr);
      fprintf(fichier, "%ft%fn", celsius, fahr);
      celsius = celsius + step;
   }
   return 0;
getchar();
}



mais je ne sais pas pourquoi, mais à partir de 0.83 celsius, voici ce que j'obtient:

Code :

0.820000   33.475998
0.830000   33.493999
0.839999   33.511997
0.849999   33.529999



je ne comprend pas d'où viennent les 9. pourtant, 0.83 + 0.01 donne bient 0.84, ce n'est pas une erreur d'arrondissement car il a 4 zéros de jeu. à la fin du ficher texte, voici ce que j'obtient:

Code :

299.981476   571.966675
299.991486   571.984680



ce qui est quand même assez loin du 300 attendu.


merci pour vos réponses.
----------
AMD ***Athlon XP Barton 2600+ @ 2.046 GHz***178 fsb L2 512Kb --- ***768 DDR***Ram --- XFX ***GeForce4 ti4200***128 Mo
- Haut de page -
noxyd
modérateur HA-Vente
Membre # 12025

 Avatar du membre
Lieu : LYS/LFLL

Messages :
4161 (2.32 par jour)


Score :

Message du 23-06-2006 @ 8:42   Site personnel   Afficher le profil   Envoyer un message privé   Editer le message   Citer le message      Afficher l'adresse IP   Alerter les modérateurs   

essaye déja en remplacant tes %f par %.2f pour voir.
----------
Canon EOS 350D/ Sigma EX 100-300 f/4 HSM

HP 8510p : Radeon HD2600 256Mb/2Go/120Go 7200rpm/WSXGA+ du bonheur!

Mes photos:Airliners/Lyon Spotting
- Haut de page -
$AX$
Membre hyperactif
Membre # 17796

 Avatar du membre
Lieu : Paris même

Messages :
107 (0.08 par jour)




Message du 23-06-2006 @ 8:50   Site personnel   Afficher le profil   Envoyer un message privé   Editer le message   Citer le message      Afficher l'adresse IP   Alerter les modérateurs   

Pas mieux...

... ou remplace tes "float" par des "double"
----------
Compal CL56 GBM 510d Spezial
Centrino 1.7GHz - 2x512 Mo - Hitachi 7K60 - ATI 9700 128 Mo
- Haut de page -
UdoBoth
Membre
Membre # 24963

 Avatar du membre
Lieu : 91-Orsay

Messages :
35 (0.04 par jour)


Score :

Message du 23-06-2006 @ 10:41   Afficher le profil   Envoyer un message privé   Editer le message   Citer le message      Afficher l'adresse IP   Alerter les modérateurs   

C'est Mr. Farenheit....

C'est tout le problème de la représentation des réels en binaire, du nombre de chiffres significatifs alloués à la mantisse (les nombres sont sous la forme mantisse * exposant - choix float <-> double).
Si le compilateur C n'optimise pas les opérations, il peut y avoir intérêt à poser l'opération dans l'ordre * puis /
bien qu'elle soit commutative en théorie.
300 ou 299,991 c'est pareil à quelques 10 puissance -5 près (en "double" ce sera peut-être mieux, sinon forcer l'arrondi)
Courage, le calcul scientifique est plein de surprises....

----------
Il existe 10 sortes de gens :Ceux qui comprennent le binaire et... ceux qui ne le comprennent pas.
- Haut de page -
Black_Knight
Membre hyperactif
Membre # 7740

 Avatar du membre
Lieu : Cornwall, Ontario, Canada

Messages :
234 (0.11 par jour)


Score :

Message du 23-06-2006 @ 18:28   Site personnel   Afficher le profil   Envoyer un message privé   Editer le message   Citer le message      Afficher l'adresse IP   Alerter les modérateurs   

j'ai essayé en double, et les réponses sont exactes, en effet. Mais je ne comprend toujours pas trop pourquoi ça ne marche pas en float...
----------
AMD ***Athlon XP Barton 2600+ @ 2.046 GHz***178 fsb L2 512Kb --- ***768 DDR***Ram --- XFX ***GeForce4 ti4200***128 Mo
- Haut de page -
marsu_381
Membre actif
Membre # 12502

 
Lieu : versailles

Messages :
70 (0.04 par jour)


Score :

Message du 23-06-2006 @ 23:44   Afficher le profil   Envoyer un message privé   Editer le message   Citer le message      Afficher l'adresse IP   Alerter les modérateurs   

une autre hypotèse, au niveau de cette ligne :
fahr = ( celsius / 5 * 9 ) + 32

essaye de remplacer les entiers par des décimaux.

- Haut de page -
Black_Knight
Membre hyperactif
Membre # 7740

 Avatar du membre
Lieu : Cornwall, Ontario, Canada

Messages :
234 (0.11 par jour)


Score :

Message du 24-06-2006 @ 5:26   Site personnel   Afficher le profil   Envoyer un message privé   Editer le message   Citer le message      Afficher l'adresse IP   Alerter les modérateurs   

Citation du message de marsu_381 :

une autre hypotèse, au niveau de cette ligne :
fahr = ( celsius / 5 * 9 ) + 32

essaye de remplacer les entiers par des décimaux.



j'ai essayer, mais rien à faire. le résultat est exactement le même que lors du premier post. Mais je crois que cette technique fonctionne uniquement lors que le résultat est tronqué. Ainsi, en divisant par un nombre à virgule, le résultat n'est pas tronqué car l'ordinateur le voit une division de 2 nombres de même type.

EDIT: Une chose est certaine, ce n'est pas la faute d'un compilateur capricieux. j'ai tester avec Open Watcom, Digital Mars ainsi que SilverFrost FTN95. (et étonnement, FTN95, un compilateur fortran, produit l'exécutable le moins volumineux.)

[message édité le 24-06-2006 @ 5:40 Par Black_Knight]
----------
AMD ***Athlon XP Barton 2600+ @ 2.046 GHz***178 fsb L2 512Kb --- ***768 DDR***Ram --- XFX ***GeForce4 ti4200***128 Mo
- Haut de page -
UdoBoth
Membre
Membre # 24963

 Avatar du membre
Lieu : 91-Orsay

Messages :
35 (0.04 par jour)


Score :

Message du 25-06-2006 @ 12:11   Afficher le profil   Envoyer un message privé   Editer le message   Citer le message      Afficher l'adresse IP   Alerter les modérateurs   

Bonjour,

Il ne faut pas se laisser abuser par la valeur décimale des nombres et croire que parce qu'on additionne 0.01 + 0.01 à l'infini (jusqu'à 300 ici...) le résultat DOIT tomber juste en décimal. Le CPU du PC ne compte pas en décimal...
Les nombres sont convertis en binaire -> calcul -> reconversion en décimal pour présentation.
Le calcul avec des ENTIERS tombera juste tant que les nombres (et les résultats intermédiaires...) ne dépassent pas +- 32767 (avec mots de 16 bits "WORD"), +- 2147483647 (avec mots de 32 bits "INTEGER"), encore plus en mots de 64 bits...
Le calcul avec des RéELS est un faux ami.... selon le nombre de bits alloués à la MANTISSE la représentation du nombre de départ peut déjà être approximative dès la conversion en binaire. Le réel est stocké sous la forme
(a 1/2 + b 1/4 + c 1/8 + d 1/16 + e.....) * 2**n avec a, b, c, d.... valant 0 ou 1, et n limité au format de l'EXPOSANT de 2 qui multiplie la mantisse.
Les TYPES de variables FLOAT, DOUBLE, LONG DOUBLE correspondent à des formats de plus en plus généreux en nombre de bits alloués pour la mantisse et l'exposant.
La conséquence porte sur le nombre de chiffres significatifs du résultat. Il est illusoire de dépasser 4 chiffres en FLOAT, mais l'ordre de grandeur est bon. Il convient donc de limiter l'affichage au nombre de chiffres qui ont un sens !

COMPLEMENT
La norme IEEE 754 puis 854 définit la représentation flottante des réels (voir avec Google...)
Est-ce que ton compilateur génère des "FLOAT" avec 23 bits de mantisse ou moins ?
Le réel 0.01 n'a pas de contrepartie exacte en flottant, une erreur systématique s'accumule donc à chaque addition et finit par se voir lors de la conversion en décimal.


[message édité le 25-06-2006 @ 18:45 Par UdoBoth]
----------
Il existe 10 sortes de gens :Ceux qui comprennent le binaire et... ceux qui ne le comprennent pas.
- Haut de page -
Gnux
Master
Membre # 4366

 
Lieu : Belgique

Messages :
875 (0.38 par jour)


Score :

Message du 25-06-2006 @ 19:17   Site personnel   Afficher le profil   Envoyer un message privé   Editer le message   Citer le message      Afficher l'adresse IP   Alerter les modérateurs   

Si tu veux plus de détails (voir les chapitres 1 & 2) : http://www.ulb.ac.be/di/map/gbonte/InfoF205.html#contenu
Ce n'est pas une blague, le cours est abordable ! :)

----------
Lenovo Thinkpad X60s
- Haut de page -
Black_Knight
Membre hyperactif
Membre # 7740

 Avatar du membre
Lieu : Cornwall, Ontario, Canada

Messages :
234 (0.11 par jour)


Score :

Message du 26-06-2006 @ 18:50   Site personnel   Afficher le profil   Envoyer un message privé   Editer le message   Citer le message      Afficher l'adresse IP   Alerter les modérateurs   

merci énormément à vous deux, je crois que je commence à comprendre... :D
----------
AMD ***Athlon XP Barton 2600+ @ 2.046 GHz***178 fsb L2 512Kb --- ***768 DDR***Ram --- XFX ***GeForce4 ti4200***128 Mo
- Haut de page -


Aller dans le forum :  

Plan du forum | Contacter l'administrateur

Powered by SoulBB 3.0.1
© Soulmanto, 2003-2006

Valid XHTML 1.0 Transitional

Page générée en 0.124 secondes