IdentifiantMot de passe
Loading...
Mot de passe oublié ?Je m'inscris ! (gratuit)
Navigation

Inscrivez-vous gratuitement
pour pouvoir participer, suivre les réponses en temps réel, voter pour les messages, poser vos propres questions et recevoir la newsletter

C Discussion :

Afficher plus que 6 décimales avec une variable de type double, comment ?


Sujet :

C

  1. #1
    Membre régulier
    Profil pro
    Inscrit en
    Août 2006
    Messages
    256
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Août 2006
    Messages : 256
    Points : 91
    Points
    91
    Par défaut Afficher plus que 6 décimales avec une variable de type double, comment ?
    Bonjours,

    Je suis en train de faire un petit programme qui fait un certain calcul, mais je n'arrive pas à afficher plus que 6 décimale, que ça soit en console (win) ou avec une MessageBox.

    La variable des de type double et en console je l'affiche avec printf("%f", variable);

    Voilà, si vous avez une idée, elle est bienvenue.

    Sinon, un peu à pars, mais comment savoir avec combien de décimale bosse le programme, et sans utiliser de librairie spéciale, quel est le type de variable avec lequel a la plus grande précision de calcul.
    Je fait un programme de calcul topographique, est-ce que j'aurais intérer à m'orienter vers une librairie qui calcul avec plus de précision (je crois que j'en avais entendu parlé une fois, ou c'étais pour manipuler de grand chiffres)

    Merci.
    A+, Pierre.

  2. #2
    Membre éprouvé Avatar de zooro
    Homme Profil pro
    Développeur Java
    Inscrit en
    Avril 2006
    Messages
    921
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 45
    Localisation : France, Marne (Champagne Ardenne)

    Informations professionnelles :
    Activité : Développeur Java

    Informations forums :
    Inscription : Avril 2006
    Messages : 921
    Points : 1 260
    Points
    1 260
    Par défaut
    Citation Envoyé par Pierre.g
    Je suis en train de faire un petit programme qui fait un certain calcul, mais je n'arrive pas à afficher plus que 6 décimale, que ça soit en console (win) ou avec une MessageBox.
    La variable des de type double et en console je l'affiche avec printf("%f", variable);
    Voilà, si vous avez une idée, elle est bienvenue.
    Essaie comme ça :
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    double dou = 4.1234567890;
    printf("dou='%.10f'\n", dou);
    cf. le man de printf
    [alkama] quelqu'un est allé voir la guerre des mondes?
    [@Chrisman] j'espère pour spielberg
    --- bashfr.org

  3. #3
    Membre régulier
    Profil pro
    Inscrit en
    Août 2006
    Messages
    256
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Août 2006
    Messages : 256
    Points : 91
    Points
    91
    Par défaut
    Ah oui, bien joué, j'avais essayé %10f, mais je ne savais pas que ça définissait seulement le nombre de chiffre avant la virgule et pas après.

    Merci bien.
    A+, Pierre.

  4. #4
    Expert éminent sénior

    Profil pro
    Inscrit en
    Janvier 2007
    Messages
    10 603
    Détails du profil
    Informations personnelles :
    Âge : 66
    Localisation : France

    Informations forums :
    Inscription : Janvier 2007
    Messages : 10 603
    Points : 17 913
    Points
    17 913
    Billets dans le blog
    2
    Par défaut
    Citation Envoyé par Pierre.g
    Ah oui, bien joué, j'avais essayé %10f, mais je ne savais pas que ça définissait seulement le nombre de chiffre avant la virgule et pas après.

    Merci bien.
    A+, Pierre.

    FAUX

    ça désigne le nombre TOTAL de chiffres, incluant avant, après ET la virgule.
    "Un homme sage ne croit que la moitié de ce qu’il lit. Plus sage encore, il sait laquelle".

    Consultant indépendant.
    Architecture systèmes complexes. Programmation grosses applications critiques. Ergonomie.
    C, Fortran, XWindow/Motif, Java

    Je ne réponds pas aux MP techniques

  5. #5
    Membre éprouvé Avatar de zooro
    Homme Profil pro
    Développeur Java
    Inscrit en
    Avril 2006
    Messages
    921
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 45
    Localisation : France, Marne (Champagne Ardenne)

    Informations professionnelles :
    Activité : Développeur Java

    Informations forums :
    Inscription : Avril 2006
    Messages : 921
    Points : 1 260
    Points
    1 260
    Par défaut
    Citation Envoyé par souviron34
    ça désigne le nombre TOTAL de chiffres, incluant avant, après ET la virgule.
    Oui, je me suis fait avoir plusieurs fois
    [alkama] quelqu'un est allé voir la guerre des mondes?
    [@Chrisman] j'espère pour spielberg
    --- bashfr.org

  6. #6
    Membre régulier
    Profil pro
    Inscrit en
    Août 2006
    Messages
    256
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Août 2006
    Messages : 256
    Points : 91
    Points
    91
    Par défaut
    Ok, merci pour cette précision.

    Sinon, pour faire des calculs plus précis, si il y en a que ça intéresse j'ai trouvé.
    Ça s'appelle faire des calculs avec une précision arbitraire ("arbitrary precision" en anglais). Les calculs sont (beaucoup, mais encore négligeable ?) plus lent, mais on peut préciser le nombre de chiffre après la virgule que l'on veut pour le résultat.

    Il existe pas mal de librairie en C pour faire ce genre ce calculs, voir par exemple GMP ("GNU Multiple Precision Arithmetic Library") : gmplib.org.

    Je vais essayer ça voir déjà si j'arrive à l'utiliser, et ensuite voir de combien changent les résultats de mes calculs (j'espère que ça sais calculer avec des fonctions mathématique comme exponentiel, ln, ...)

    A+, Pierre.

  7. #7
    Expert éminent sénior

    Profil pro
    Inscrit en
    Janvier 2007
    Messages
    10 603
    Détails du profil
    Informations personnelles :
    Âge : 66
    Localisation : France

    Informations forums :
    Inscription : Janvier 2007
    Messages : 10 603
    Points : 17 913
    Points
    17 913
    Billets dans le blog
    2
    Par défaut
    je ne vois pas pourquoi tu aurais besoin de telles bibliothèques... Avec des doubles, tu as droit à 10^-16 de précision... ça te suffit pas ??????????????
    "Un homme sage ne croit que la moitié de ce qu’il lit. Plus sage encore, il sait laquelle".

    Consultant indépendant.
    Architecture systèmes complexes. Programmation grosses applications critiques. Ergonomie.
    C, Fortran, XWindow/Motif, Java

    Je ne réponds pas aux MP techniques

  8. #8
    Expert éminent sénior
    Avatar de Emmanuel Delahaye
    Profil pro
    Retraité
    Inscrit en
    Décembre 2003
    Messages
    14 512
    Détails du profil
    Informations personnelles :
    Âge : 67
    Localisation : France, Paris (Île de France)

    Informations professionnelles :
    Activité : Retraité

    Informations forums :
    Inscription : Décembre 2003
    Messages : 14 512
    Points : 20 985
    Points
    20 985
    Par défaut
    Citation Envoyé par souviron34
    Avec des doubles, tu as droit à 10^-16 de précision...
    Ca dépend de l'implémentation. Voir <limits.h> et/ou <float.h>
    Pas de Wi-Fi à la maison : CPL

  9. #9
    Membre régulier
    Profil pro
    Inscrit en
    Août 2006
    Messages
    256
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Août 2006
    Messages : 256
    Points : 91
    Points
    91
    Par défaut
    Citation Envoyé par souviron34
    je ne vois pas pourquoi tu aurais besoin de telles bibliothèques... Avec des doubles, tu as droit à 10^-16 de précision... ça te suffit pas ??????????????
    Apparament, ce que j'ai compris, c'est que le résultat de chaque calcul élémentaire (multiplication, division, ...) est arrondis à 17 chiffres (avant la virgule + après la virgule = 17).
    Ce qui fait que calculs après calculs, le résultat est un peu plus faux.

    Ce que je voulais vérifier c'est de combien il était faux, j'ai essayé avec un calcul d'altération linéaire (on s'en sert en topographie) avec une précision de 5000 chiffres, ce qui m'a permis de déterminer que le résultat de ces calculs en double précision est faux à partir de 10^-10.

    Donc effectivement, sachant que c'est une valeur en millimètres et que je vais l'arrondire au dixième parce que c'est le bout du monde en topo, je n'ai pas besoin d'utiliser une telle librairie pour ce calcul.

    Par contre pour d'autre calculs avec plus d'opérations, je serais peut-être ammené à l'utiliser.

    Si je me suis trompé dans mon résonnement, n'hésitez pas à me corriger, au contraire.

    Merci.
    A+, Pierre.

  10. #10
    Expert éminent

    Inscrit en
    Novembre 2005
    Messages
    5 145
    Détails du profil
    Informations forums :
    Inscription : Novembre 2005
    Messages : 5 145
    Points : 6 911
    Points
    6 911
    Par défaut
    Citation Envoyé par Pierre.g
    Apparament, ce que j'ai compris, c'est que le résultat de chaque calcul élémentaire (multiplication, division, ...) est arrondis à 17 chiffres (avant la virgule + après la virgule = 17).
    Ce qui fait que calculs après calculs, le résultat est un peu plus faux.
    Presque cela. L'arrondi se fait sous forme binaire. Si tu veux analyser ce qui se passe, il faut en tenir compte.

    Ce que je voulais vérifier c'est de combien il était faux, j'ai essayé avec un calcul d'altération linéaire (on s'en sert en topographie) avec une précision de 5000 chiffres, ce qui m'a permis de déterminer que le résultat de ces calculs en double précision est faux à partir de 10^-10.
    * Une autre technique est de faire le calcul en float et en double.
    * Une autre technique est d'utiliser du calcul d'intervalle.
    * Il est parfois possible de faire le même calcul en perdant moins de précision.
    Les MP ne sont pas là pour les questions techniques, les forums sont là pour ça.

  11. #11
    Membre régulier
    Profil pro
    Inscrit en
    Août 2006
    Messages
    256
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Août 2006
    Messages : 256
    Points : 91
    Points
    91
    Par défaut
    "L'arrondi se fait sous forme binaire."

    Il y a quoi comme différence avec les arrondis "classiques". J'avais cru comprendre que c'était les "algorithmes internes" (je ne sais pas trop comment on appelle ça) du processeur qui arrondissaient un peu comme ils voulaient. C'est ce que mettent pas mal en avant les créateurs des librairies de calcul en précision arbitraire, parce qu'apparament, sur deux processeurs différents, on n'est pas sûr de retrouver exactement le même résultat (même si bien sûr la grande majoritée des processeurs sortirons le même résultat et l'erreur sortie par les autre sera juste un "arrondis" différent apparament).


    "Une autre technique est de faire le calcul en float et en double."
    Le calcul que j'ai fait était déjà en double.

    "Une autre technique est d'utiliser du calcul d'intervalle."
    C'est ce que font les librairies de calcul avec précision arbitraire ça, non ?

    "Il est parfois possible de faire le même calcul en perdant moins de précision."
    Justement, je me posais une question, et tu est peut être en train d'y répondre :


    Si l'on fait un programme qui calcul :

    a = b * c;
    d = a * z;

    On supose que le résultat de b * c est arrondis par le processeur, et qu'on le stock dans une variable, ensuite un continus les calcule à partir ce cette variable.

    Est-ce que dans ce cas, d'avoir codé :

    d = b * c * z;

    aurait évité au processeur d'arrondir (b * c) et ainsi d'avoir un résultat un tout petit peu plus juste ?

    En gros, est-ce que le processeur garde en interne une plus grande précision qu'un chiffre stoqué dans un double ?

    Et au passage, existe-il un type de variable pour les flotants plus "gros" (qui stoque plus de chiffres/décimales) que le double ?

    Merci.
    A la prochaine, Pierre.

  12. #12
    Expert éminent

    Inscrit en
    Novembre 2005
    Messages
    5 145
    Détails du profil
    Informations forums :
    Inscription : Novembre 2005
    Messages : 5 145
    Points : 6 911
    Points
    6 911
    Par défaut
    Citation Envoyé par Pierre.g
    "L'arrondi se fait sous forme binaire."

    Il y a quoi comme différence avec les arrondis "classiques". J'avais cru comprendre que c'était les "algorithmes internes" (je ne sais pas trop comment on appelle ça) du processeur qui arrondissaient un peu comme ils voulaient.
    La norme IEEE754 impose l'équivalent d'un calcul avec une précision infinie puis un arrondi suivant un parmi quatres modes (lequel est choisi par l'utilisateur) pour une série d'opération (+, -, *, /, racine carrée). Pour le reste (en particulier pour les opérations transcendantes), c'est plus libre. Demander cette précision est quasiment impossible, mais demander que l'arrondi introduise une erreur de moins d'un peu plus qu'un demi ULP, c'est possible.

    C'est ce que mettent pas mal en avant les créateurs des librairies de calcul en précision arbitraire, parce qu'apparament, sur deux processeurs différents, on n'est pas sûr de retrouver exactement le même résultat (même si bien sûr la grande majoritée des processeurs sortirons le même résultat et l'erreur sortie par les autre sera juste un "arrondis" différent apparament).
    On peut considérer que sur le point ci-dessus, tous les processeurs respectent IEEE 754 (sur les dénormaux, c'est différent).

    Hors calcul transcendant et fonctions de bibliothèques, les différences d'arrondi à ma connaissance proviennent principalement d'autres facteurs. En particulier des compilateurs qui -- surtout avec l'optimisation activée -- réordonne le code et vont changer l'ordre (ou profiter d'un ordre indéfini) des calculs, donc changer les arrondis. Une autre possibilité est de profiter de la license qu'offre le C de faire certains calculs en précision plus grande que celle demandée par les types.

    (Note que gcc a un bug fort visible avec linux sur x86 et fait souvent des calculs dans une précision plus grande, même quand ce n'est pas autorisé.)

    "Une autre technique est de faire le calcul en float et en double."
    Le calcul que j'ai fait était déjà en double.
    Faire le calcule en float et en double et comparer les résultats.

    "Une autre technique est d'utiliser du calcul d'intervalle."
    C'est ce que font les librairies de calcul avec précision arbitraire ça, non ?
    Non. Le calcul d'intervalle utilise deux doubles qui encadrent la valeur exacte.

    "Il est parfois possible de faire le même calcul en perdant moins de précision."
    Justement, je me posais une question, et tu est peut être en train d'y répondre :


    Si l'on fait un programme qui calcul :

    a = b * c;
    d = a * z;

    On supose que le résultat de b * c est arrondis par le processeur, et qu'on le stock dans une variable, ensuite un continus les calcule à partir ce cette variable.

    Est-ce que dans ce cas, d'avoir codé :

    d = b * c * z;

    aurait évité au processeur d'arrondir (b * c) et ainsi d'avoir un résultat un tout petit peu plus juste ?

    En gros, est-ce que le processeur garde en interne une plus grande précision qu'un chiffre stoqué dans un double ?
    C'est un des cas où un compilateur C peut générer du code qui va le faire.

    Et au passage, existe-il un type de variable pour les flotants plus "gros" (qui stoque plus de chiffres/décimales) que le double ?
    long double mais ce n'est pas garanti d'une part -- et d'autre part certains implémentent des long doubles en soft qui sont donc beaucoup plus lent que double avec un support hard.
    Les MP ne sont pas là pour les questions techniques, les forums sont là pour ça.

  13. #13
    Membre régulier
    Profil pro
    Inscrit en
    Août 2006
    Messages
    256
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Août 2006
    Messages : 256
    Points : 91
    Points
    91
    Par défaut
    OK, merci pour ces précisions.

    A+, Pierre.

  14. #14
    Membre éprouvé

    Profil pro
    Inscrit en
    Juin 2006
    Messages
    1 116
    Détails du profil
    Informations personnelles :
    Âge : 38
    Localisation : France

    Informations forums :
    Inscription : Juin 2006
    Messages : 1 116
    Points : 1 111
    Points
    1 111
    Par défaut
    Je précise que pour que Robert Gosseyn arrive à se téléporter, il faut qu'il ajuste les flux énergétique à la 22ème décimale près

  15. #15
    Membre régulier
    Profil pro
    Inscrit en
    Août 2006
    Messages
    256
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Août 2006
    Messages : 256
    Points : 91
    Points
    91
    Par défaut
    kromartien, c'est pas parce que tu n'arrive visiblement pas à voir à quoi ça peut servir que tu a besoin de troller ...

  16. #16
    Membre éprouvé

    Profil pro
    Inscrit en
    Juin 2006
    Messages
    1 116
    Détails du profil
    Informations personnelles :
    Âge : 38
    Localisation : France

    Informations forums :
    Inscription : Juin 2006
    Messages : 1 116
    Points : 1 111
    Points
    1 111
    Par défaut
    désolé pour cette blague je ne voulais pas troller. Peut être pouvez vous jeter un coup d'oeil à la représentation binaire des nombres à virgule flottante. Ainsi, ça donne une certaine idée de ce qui est réalisé à chaque calcul, et de la précision perdue. 1.2 * 1.2 = 1.44 , si la deuxième décimale n'est pas prise en compte par le type du contenant, l'arrondi est à la deuxième décimale. Je ne sais pas vraiment comment est réalisé l'arrondi, j'imagine que c'est un arrondi et non une troncature.

+ Répondre à la discussion
Cette discussion est résolue.

Discussions similaires

  1. Réponses: 4
    Dernier message: 06/08/2010, 22h13
  2. Problème bizarre avec une variable de type string
    Par beegees dans le forum VB 6 et antérieur
    Réponses: 2
    Dernier message: 10/06/2009, 11h34
  3. Problème avec une variable de type objet
    Par mrocks dans le forum C#
    Réponses: 7
    Dernier message: 09/05/2009, 22h27
  4. afficher plus que 23:59 avec un DateTime
    Par TrollTop dans le forum VC++ .NET
    Réponses: 2
    Dernier message: 11/10/2007, 15h56
  5. problème avec une variable de type string
    Par marsupilami34 dans le forum Macros et VBA Excel
    Réponses: 3
    Dernier message: 14/06/2007, 14h53

Partager

Partager
  • Envoyer la discussion sur Viadeo
  • Envoyer la discussion sur Twitter
  • Envoyer la discussion sur Google
  • Envoyer la discussion sur Facebook
  • Envoyer la discussion sur Digg
  • Envoyer la discussion sur Delicious
  • Envoyer la discussion sur MySpace
  • Envoyer la discussion sur Yahoo