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 :

Conversion de struct timeval en double.


Sujet :

C

  1. #1
    Membre du Club
    Homme Profil pro
    Étudiant
    Inscrit en
    Février 2020
    Messages
    63
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 24
    Localisation : France, Bas Rhin (Alsace)

    Informations professionnelles :
    Activité : Étudiant

    Informations forums :
    Inscription : Février 2020
    Messages : 63
    Points : 50
    Points
    50
    Par défaut Conversion de struct timeval en double.
    Bonjour.
    Je cherche à convertir une struct timeval en double.

    J'ai bricolé quelquechose, qui semble fonctionner :
    Code C : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
     
    double tvtod(struct timeval tv)
    {
        char*sec=malloc(sizeof(long double));
        sprintf(sec,"%ld",tv.tv_sec);
     
        char*usec=malloc(sizeof(long double));
        sprintf(usec,"%ld",tv.tv_usec);
     
        char*temps=malloc(2*sizeof(long double)+8);
        strcat(temps,sec);
        strcat(temps,".");
        strcat(temps,usec);
     
        double tps =strtod(temps,NULL);
     
        free(sec);
        free(usec);
        free(temps);
     
    return tps;
    }

    Cette fonction semble bien fonctionner mais au bout de 7 appels elle crache en segfault ...
    Si quelqu'un a une idée pour régler le soucis ou a une autre proposition je suis preneur.

    Merci !

  2. #2
    Expert éminent
    Homme Profil pro
    Ingénieur développement matériel électronique
    Inscrit en
    Décembre 2015
    Messages
    1 562
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 60
    Localisation : France, Bouches du Rhône (Provence Alpes Côte d'Azur)

    Informations professionnelles :
    Activité : Ingénieur développement matériel électronique
    Secteur : High Tech - Électronique et micro-électronique

    Informations forums :
    Inscription : Décembre 2015
    Messages : 1 562
    Points : 7 628
    Points
    7 628
    Par défaut
    Bonjour,

    Tout d'abord la solution, tu veux convertir des secondes et microsecondes en secondes donc :
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    return  tv.tv_sec + tv.tv_usec / 1000000.;
    Maintenant bricolage désigne bien ce que tu as fait :
    On utilise malloc() quand on crée un objet qui :
    - va perdurer au delà de la fonction;
    - ou est de taille gigantesque;
    - ou n'a pas de majorant de taille raisonnable.
    Tu n'es dans aucun de ces cas, donc pas besoin de malloc().
    Il faut donc utiliser des tableaux de char. On n'en connait pas la taille, si on doit y mette "1" il faut 2 octets, si on veut avoir "18446744073709551615" il faut 21 octets. Je n'ai pas choisi ce nombre au hasard, c'est plus grand entier que l'on peut représenter et en secondes il correspond à 584542 milliards d'années (et en µsec à 584542 ans). Des tableaux de 21 char seraient donc amplement suffisants.

    La taille que tu as réservée ne correspond à rien c'est la taille en mémoire (donc en base 256 pas en base 10) d'un long double qui peut stocker des nombres bien plus grands mais ne fait que 8 ou 10 octets. Donc le plus grand nombre pour lui serait "9999999", le nombre de secondes peut dépasser cette valeur (10000000s correspond à 116 jours.)
    Ensuite tu utilises un sprintf() en précisant le format "%ld", ce format doit indiquer le type de tv.tv_sec qui est int, ça n'est pas le bon format.

    Ensuite tu écris strcat(temps,sec);, tu concatènes donc une variable aléatoire et ta chaine sec, là encore ça peut donner n'importe quoi.

    Pour finir tu penses que la concaténation te donnera le bon nombre, est-ce que concaténer 1s et 1µs soit "1", "." et "1" te donneras la réponse "1.000001" ?

  3. #3
    Expert éminent sénior
    Avatar de Sve@r
    Homme Profil pro
    Ingénieur développement logiciels
    Inscrit en
    Février 2006
    Messages
    12 631
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France, Oise (Picardie)

    Informations professionnelles :
    Activité : Ingénieur développement logiciels
    Secteur : Aéronautique - Marine - Espace - Armement

    Informations forums :
    Inscription : Février 2006
    Messages : 12 631
    Points : 30 865
    Points
    30 865
    Billets dans le blog
    1
    Par défaut
    Bonjour
    Citation Envoyé par auloma Voir le message
    J'ai bricolé quelquechose, qui semble fonctionner :
    Ouch, bricolage et C ne vont pas bien ensembles (d'ailleurs, même pour tout, bricolage ne semble pas être synonyme de "travail de qualité") . Et malheureusement, "semble fonctionner" n'est pas suffisant pour pouvoir dire qu'un code est correct.
    Déjà, pourquoi ces malloc ? (ex char *sec=malloc(sizeof(long double))) ? Quand tu veux un int i, vas-tu écrire int *i=malloc(sizeof(int)) ??? Tu veux un long double tu le demandes tout simplement, comme quand tu faisais au tout début de ton apprentissage avant de connaitre malloc (ex long double sec). Mais même si ton kif est d'allouer la mémoire pour tes variables simples (ok tu en as le droit), surtout tu ne stockes pas cette adresse de long double dans un truc prévu pour recevoir une adresse de char. Ok une adresse c'est toujours une adresse, mais en écrivant char *sec tu dis explicitement au compilo "vas-y en confiance, à cette adresse tu trouveras un char" (un octet) or à cette adresse il y a un long double (10 octets !!!), franchement tu ne l'aides pas à s'en sortir !!! Accessoirement utiliser du double pour stocker des secondes entières...
    Pour le reste, dalfab a bien expliqué le truc bien qu'il me semble que le time_t soit signé, ne serait-ce que pour pouvoir calculer des dates d'avant l'epoch Unix (1/1/70) donc seulement 63 bits au lieu de 64 mais bon, 584 milliards ou seulement 292 milliards d'années on s'en bat un peu le steak non ?
    Mon Tutoriel sur la programmation «Python»
    Mon Tutoriel sur la programmation «Shell»
    Sinon il y en a pleins d'autres. N'oubliez pas non plus les différentes faq disponibles sur ce site
    Et on poste ses codes entre balises [code] et [/code]

  4. #4
    Membre du Club
    Homme Profil pro
    Étudiant
    Inscrit en
    Février 2020
    Messages
    63
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 24
    Localisation : France, Bas Rhin (Alsace)

    Informations professionnelles :
    Activité : Étudiant

    Informations forums :
    Inscription : Février 2020
    Messages : 63
    Points : 50
    Points
    50
    Par défaut
    Effectivement j'ai agi un peu trop dans la précipitation et fait du grand n'importe quoi.
    Merci pour vos éclaircissements !

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

Discussions similaires

  1. Conversion d'un Decimalformat en double
    Par encours dans le forum Langage
    Réponses: 3
    Dernier message: 30/08/2011, 19h42
  2. Conversion d'un byte[] en double
    Par erkan37 dans le forum Général Java
    Réponses: 7
    Dernier message: 14/04/2008, 16h50
  3. Conversion de chaîne "" en type Double non valide
    Par vérokit dans le forum VB.NET
    Réponses: 2
    Dernier message: 10/04/2008, 09h14
  4. Problèmes de conversion d'une chaine en double
    Par glycerine dans le forum Débuter
    Réponses: 3
    Dernier message: 31/07/2007, 16h05
  5. [Conversion]Probleme de calcul en double et en floatant
    Par TOPGUN89 dans le forum Général Java
    Réponses: 2
    Dernier message: 18/04/2005, 18h46

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