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 :

affichier un vector de type cvPoint2D32f


Sujet :

C++

  1. #1
    Membre régulier
    Enseignant Chercheur
    Inscrit en
    Décembre 2011
    Messages
    172
    Détails du profil
    Informations professionnelles :
    Activité : Enseignant Chercheur

    Informations forums :
    Inscription : Décembre 2011
    Messages : 172
    Points : 73
    Points
    73
    Par défaut affichier un vector de type cvPoint2D32f
    bonjour
    je suis débutante en c++, dans mon travail j'utilise la bibliothèque opencv,
    ma question est la suivante: comment je peux afficher un vecteur de type cvPoint2D32f dans un fichier texte?
    j'ai essayer ces instructions :

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
     
    ofstream fichier ("D:\\test.txt", ios::out | ios::trunc);
    if(fichier){
    for (int i=0;i<pointsout.size(); i++){
    fichier<< pointsout[i]>>std::endl;
    }
    fichier.close();
    }
    alors j'obtiens le message d'erreur suivant:
    error: no match for 'operator <<' in fichier<<pointsout.std::vector<_Tp,_Alloc:::operator[] [with_Tp=CvPoint2D32f, alloc= .....
    et j'ai essayer ces instructions afin d'utiliser printf:
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    for (int i=0;i<pointsout.size(); i++){
    printf("%f\t", pointsout[i]);
    }
    fichier.close();
    }
    alors j'ai obtenu l'affichage mais j'ai un problème de la conversation de CvPoint2D32f.

    j’espère bien trouver une solution rapide. Merci d'avance

  2. #2
    Membre émérite
    Profil pro
    Inscrit en
    Novembre 2004
    Messages
    2 764
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Novembre 2004
    Messages : 2 764
    Points : 2 705
    Points
    2 705
    Par défaut
    Il faut définir l'opérateur de flux << pour la structure CvPoint2D32f.

    Ou alors, tu accèdes individuellement à ses membres.

  3. #3
    Expert éminent sénior
    Avatar de koala01
    Homme Profil pro
    aucun
    Inscrit en
    Octobre 2004
    Messages
    11 614
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 52
    Localisation : Belgique

    Informations professionnelles :
    Activité : aucun

    Informations forums :
    Inscription : Octobre 2004
    Messages : 11 614
    Points : 30 626
    Points
    30 626
    Par défaut
    Salut,

    Il y a déjà une petite erreur dans le code
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
     
     
    ofstream fichier ("D:\\test.txt", ios::out | ios::trunc);
    if(fichier){
    for (int i=0;i<pointsout.size(); i++){
    fichier<< pointsout[i]>>std::endl;
    }
    fichier.close();
    }
    qui devrait être
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    /* la classe ofstream est, d'office, un fichier ouvert en écriture
     *
     * il n'est donc pas utile ni nécessaire de rajouter ios::out comme paramètre
     */
    ofstream fichier ("D:\\test.txt", ios::trunc);
    if(fichier){
    for (int i=0;i<pointsout.size(); i++){
    fichier<< pointsout[i]<<std::endl;
    }
    //Dans une fonction qui ne ferait que ca, la ligne suivante est inutile
    fichier.close();
    }
    (les chevrons doivent tous aller dans le même sens )

    Ceci dit, le compilateur te dit exactement ce qui ne va pas dans le message qu'il t'envoie: il ne trouve aucune surcharge de l'opérateur << qu'il puisse appliquer à un objet de type CvPoint2D32f!

    La raison de cette erreur est toute simple : à la base, le compilateur ne connait l'opérateur << que pour les types primitifs et n'a aucune idée de la manière dont il devrait s'y prendre pour envoyer n'importe quel type défini par l'utilisateur.

    Pour résoudre ce problème, il s'agit d'indiquer au compilateur ce que tu veux qu'il envoie dans le flux lorsqu'il rencontre l'opérateur << et/ou la manière dont tu veux qu'il gère les données qu'il obtient lorsqu'il rencontre l'opérateur >>.

    Si je parle des deux en même temps, c'est parce que l'on peut assez facilement considérer que, si tu prend la peine d'écrire quelque chose dans un fichier, c'est sans doute parce que tu voudras être en mesure de récupérer ce quelque chose plus tard

    Pour que ces opérateurs soient définis pour une classe donnée, il faut
    • Soit que les opérateurs soient définis directement à l'intérieur de la classe elle-même (sous la forme d'une fonction membre)
    • Soit que les opérateurs soient définis en dehors de la classe elle-même (sous la forme d'une fonction libre)
    Comme on peut décemment estimer que les développeurs de OpenCV ne seraient pas particulièrement enchantés de constater qu'on a été tripatouiller dans les classes qu'ils ont développées, il me semble clair que nous devrons nous orienter vers une fonction libre, de manière à ne pas avoir à, justement, aller rajouter des choses au sein même de la classe CvPoint2D32f.

    Comme le nom l'indique, il semblerait que cette classe est un point 2D, qui doit donc contenir une valeur représentant l'abscisse et une autre représentant l'ordonnée.

    Comme je ne connais pas particulièrement OpenCV, je vais partir du principe que cette classe propose une fonction x() qui permet de récupérer l'abscisse et une fonction y() qui permet de récupérer l'ordonnée, mais il faudra sans doute que tu adaptes ces noms à la situation réelle

    La question qu'il nous reste à trancher, c'est de savoir si tu veux que cette fonction ne soit utilisée que pour l'écriture (respectivement la lecture) dans un fichier ou si tu veux pouvoir la réutiliser pour à peu près n'importe quel flux de sortie (respectivement n'importe quel flux d'entrée).

    On peut en effet envisager surcharger l'opérateur << de manière à ce qu'il fonctionne aussi bien avec un fichier de sortie (ofstream) qu'avec la sortie standard (cout), les flux de conversion (stringstream) ou la sortie d'erreur standard (cerr), tout comme on peut n'envisager de le surcharger que pour les fichiers de sortie.

    Pour répondre à cette question, on peut, dans un premier, temps estimer que "qui peut le plus peut le moins" et qu'il sera peut être intéressant de pouvoir afficher les valeurs des différents points ailleurs que dans un fichier.

    Si, par la suite, on se rend compte qu'il faut décidément restreindre les choses, il suffira de remplacer la classe ostream (qui est la classe de base de tous les flux de sortie formatés) par un type plus spécifique (std::ofstream, par exemple).

    La signature attendue pour l'opérateur << est du genre de std::ostream & operator <<(std::ostream & , UnType const & ).

    Nous n'avons donc qu'à remplacer UnType par le type qui nous intéresse (à savoir CvPoint2D32f) et à indiquer la manière dont on veut que les différents éléments de cette classe soient envoyés dans le flux.

    Au final, cela pourrait donc parfaitement ressembler à quelque chose comme
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    std::ostream & operator << (std::ostream & os, CvPoint2D32f const & p){
        os<<p.x() << " " <<p.y() << std::endl;
        return os;
    }
    mais si tu préfères que la sortie ressemble à
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    x = <valeur de l'abscisse> y = <valeur de l'ordonnée>
    cela prendrait sans doute la forme de
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    std::ostream & operator << (std::ostream & os, CvPoint2D32f const & p){
        os<< "x = "<<p.x() 
          << " y = " <<p.y() << std::endl;
        return os;
    }
    N'oublie pas que, si tu prévois d'être en mesure de lire un CvPoint2D32f, tu devras redéfinir l'opérateur >> correspondant.

    Pour la première version, cela pourrait ressembler (je fais vraiment simple, hein ?) à
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    std::istream & operator >> (std::istream & is, CvPoint2D32f & p){
        float x;
        float y;
        is>> x >> y;
        p = CvPoint2D32f(x,y);
        return is;
    }
    Note qu'il sera peut être intéressant de s'assurer que nous sommes bien en train de lire un point, et de la cohérence des données lues...

    Mais ca, c'est un autre débat
    A méditer: La solution la plus simple est toujours la moins compliquée
    Ce qui se conçoit bien s'énonce clairement, et les mots pour le dire vous viennent aisément. Nicolas Boileau
    Compiler Gcc sous windows avec MinGW
    Coder efficacement en C++ : dans les bacs le 17 février 2014
    mon tout nouveau blog

  4. #4
    Membre régulier
    Enseignant Chercheur
    Inscrit en
    Décembre 2011
    Messages
    172
    Détails du profil
    Informations professionnelles :
    Activité : Enseignant Chercheur

    Informations forums :
    Inscription : Décembre 2011
    Messages : 172
    Points : 73
    Points
    73
    Par défaut
    Bonjour et merci pour votre réponse.
    j'ai essayer le code comme vous m'avez proposé;
    j'ai ajouter la déclaration de la fonction comme suite:

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    std::ostream & operator << (std::ostream & os, CvPoint2D32f const & p){
        os<<p.x() << " " <<p.y() << std::endl;
        return os;
    }
    et j'ai déclaré un fichier comme ca:
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
     
    ofstream fichier ("D:\\test.txt", ios::trunc);
    et j'ai appeler la fonction pour la récupération des cordonnées (x y) comme ça:
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
     
    if(fichier){
    for (int i=0;i<pointsout.size(); i++){
    fichier<<(fichier, pointsout[k]);
    }
    j'obtiens l'erreur suivante:
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
     
    D:\\Dense.cpp||In function 'std::ostream& operator<<(std::ostream&, const CvPoint2D32f&)':| 
    D:\\Dense.cpp|13|error: 'p->CvPoint2D32f::x' cannot be used as a function| 
    D:\\Dense.cpp|13|error: 'p->CvPoint2D32f::y' cannot be used as a function|
     ||=== Build finished: 2 errors, 0 warnings ===|
    help!

  5. #5
    Expert éminent sénior
    Avatar de koala01
    Homme Profil pro
    aucun
    Inscrit en
    Octobre 2004
    Messages
    11 614
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 52
    Localisation : Belgique

    Informations professionnelles :
    Activité : aucun

    Informations forums :
    Inscription : Octobre 2004
    Messages : 11 614
    Points : 30 626
    Points
    30 626
    Par défaut
    encore une fois, le compilateur te dit exactement ce qui ne lui convient pas... Je cite :
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    'p->CvPoint2D32f::x' cannot be used as a function
    et
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    'p->CvPoint2D32f::y' cannot be used as a function
    Mais, je me cite également :
    Citation Envoyé par koala01
    Comme je ne connais pas particulièrement OpenCV, je vais partir du principe que cette classe propose une fonction x() qui permet de récupérer l'abscisse et une fonction y() qui permet de récupérer l'ordonnée, mais il faudra sans doute que tu adaptes ces noms à la situation réelle
    De toute évidence, la classe CvPoint2D32f ne présente pas de fonction nommée x() ni de fonction nommée y().

    Par contre, étant donné qu'il reconnait les membre CvPoint2D32f::x et CvPoint2D32f::y, je peux envisager deux solutions (je ne me suis pas intéressé à OpenCV depuis mon intervention précédente )
    Soit x et y sont des données publiques, et, dans ce cas, le code pour l'opérateur << ressemblerait à quelque chose de plus proche de
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    std::ostream & operator << (std::ostream & os, CvPoint2D32f const & p){
        os<<p.x << " " <<p.y << std::endl;
        return os;
    }
    Soit, les membres x et y sont privés, et la fonction qui te permet d'accéder à leur valeur est proche de getX() et getY(). Dans ce cas, le code pour l'opérateur << ressemblerait à
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    std::ostream & operator << (std::ostream & os, CvPoint2D32f const & p){
        os<<p.getX() << " " <<p.getY() << std::endl;
        return os;
    }
    Je ne vais pas commencer à vérifier ce qu'il en est dans OpenCV.

    Je t'ai expliqué le principe, j'estime l'avoir fait de manière compréhensible, à toi de te débrouiller avec la connaissance de OpenCV que tu as et que je n'ai pas pour arriver à adapter le code que je t'ai donné
    A méditer: La solution la plus simple est toujours la moins compliquée
    Ce qui se conçoit bien s'énonce clairement, et les mots pour le dire vous viennent aisément. Nicolas Boileau
    Compiler Gcc sous windows avec MinGW
    Coder efficacement en C++ : dans les bacs le 17 février 2014
    mon tout nouveau blog

  6. #6
    Membre régulier
    Enseignant Chercheur
    Inscrit en
    Décembre 2011
    Messages
    172
    Détails du profil
    Informations professionnelles :
    Activité : Enseignant Chercheur

    Informations forums :
    Inscription : Décembre 2011
    Messages : 172
    Points : 73
    Points
    73
    Par défaut
    Merci autre fois!
    j'ai essayé votre proposition:
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    os<<p.x<<" "<<p.y << std::endl
    et ça marche bien!

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

Discussions similaires

  1. Réponses: 11
    Dernier message: 15/02/2011, 17h25
  2. [STL]vector de type composé et fonction sort
    Par LordBob dans le forum SL & STL
    Réponses: 14
    Dernier message: 21/03/2007, 11h56
  3. vector et type
    Par r0d dans le forum SL & STL
    Réponses: 17
    Dernier message: 28/04/2006, 17h41
  4. Pb de conversion: double[] vers un vector type???
    Par hycsos dans le forum SL & STL
    Réponses: 4
    Dernier message: 15/01/2006, 07h59
  5. variable type tableau (vector) statique / constants
    Par Kaktus dans le forum SL & STL
    Réponses: 5
    Dernier message: 13/10/2005, 22h46

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