Partage
  • Partager sur Facebook
  • Partager sur Twitter

Fonctionnement étrange de fseek

Blocage aux '\n' lors d'un déplaçement inverse

Sujet résolu
    6 juillet 2007 à 18:57:42

    Bonjour à tous :p ,

    Je bosse actuellement sur un editeur, que je réalise avec la bibliothèque Qt.
    Le programme est pour le moment destiné à la conception de niveaux pour mon moteur de jeu isométrique (plus sympa que via un bloc-note ^^ ).
    Pour des raisons d'automatisme et de clarté, j'ai décidé de mettre en place des fichiers de configuration (.ini ou autre), pouvant être interprêtés par l'éditeur (pour le moment, mais servira pour le moteur du jeu auss) et où seraient sauvegardées toutes les données et valeurs.

    Pour cela, j'ai créé une nouvelle classe (ce genre de bibliothèqe existe très probablement, mais je le fais aussi pour m'entrainer), et j'ai implémenté toutes les fonctions que je voulais, allant de la création et l'ouverture de ces fichiers de configuration, jusqu'à l'interprétation des données contenues dans le fichier, etc.

    J'ai cependant un léger problème, lié je penses au "fseek". Lorsque j'ai besoin de me déplaçer dans le sens habituel, aucun problème; mais dés que je cherches à "rebrousser chemin" (plutôt que de chercher depuis le début), le programme semble rester bloqué aux sauts de ligne "\n"

    J'ai cru lire que fseek était assez imprévisible comme fonction, et j'aimerais donc savoir si mon problème en est la preuve ou non?
    Voila un extrait de mon code, avec la zone ciblée du bug:

    while(fgetc(m_file)!=']' && ftell(m_file)!=0)//J'ai fais une alternative au rewind
        {
        fseek(m_file,-1,SEEK_CUR);
        //Pas très propre, mais c'est juste pour tester le fontionnement dans la ligne suivante

        std::cout<<"position actuelle: "<<ftell(m_file)<<" caractere: "<<char(fgetc(m_file))<<"\n";
        //Pour Debugger

        fseek(m_file,-2,SEEK_CUR);
        //Encore pas très propre, mais c'est le seul moyen que j'ai trouvé pour "rebrousser chemin"
        }


    J'ai donc pour testé, chargé un fichier, et demandé de repérer deux éléments d'un même ensemble, tel que:

    [Groupe1]
    a=10
    b=20
    [Groupe2]
    a=15
    c=30
    [...


    Si je repère le a, puis le b, aucun problème. Par contre si je repère le b puis le a, je bloque au a :euh: , et en l'occurence juste après le "10", soit le '\n'. L'utilité de mon bout de code est de créer une alternative au rewind, car comme vous pouvez le voir, j'autorises deux éléments ayant le même nom, mais qui soient dans un groupe différent.

    Merci d'avance pour votre aide ;) , et si vous avez besoin de plus de précisions, je suis là !!
    • Partager sur Facebook
    • Partager sur Twitter
    Anonyme
      6 juillet 2007 à 19:14:15

      Salut,

      ça, c'est du C !!

      Regarde dans ma signature, ya un tuto sur fichiers en C++, si tu veut coder en C++ !

      Xav57
      • Partager sur Facebook
      • Partager sur Twitter
        6 juillet 2007 à 19:50:38

        Salut Xav57 :p ,

        Lol ^^ , pourtant je croyais bien faire :(:-° ...

        Merci en tout cas ;) , je vais procéder à la lecture de ton cours sur les fichiers et à la "conversion" de mon code, et je préviendrais si j'ai de nouveau/encore un souçi.
        • Partager sur Facebook
        • Partager sur Twitter
          7 juillet 2007 à 20:12:41

          Re :p

          J'ai donc lu ton tuto (bien réalisé d'ailleurs ;) ), et j'ai modifié mon code. Par contre, j'ai un souçi à présent (ou plutôt une contrainte), qui est que le flux n'est pas mémorisé (pas comme le pointeur "FILE*").
          Du coup, après avoir ouvert mon fichier (via une méthode de la classe) dans un fstream en membre privé de la classe, une fois que je passe à une autre méthode, le flux devient hors de portée et je n'y ai alors plus accès.

          J'ai cherché un peu sur le net, et apparemment, c'est "normal" :o , cependant, je ne vois pas comment résoudre mon problème pour le moment.
          La seule méthode qui me vient à l'esprit pour le moment, est de de charger et copier le contenu dans un cache (string, ou char[]), afin de faire les modifs, puis récupérer de nouveau le flux pour y enregistrer les données modifiées, mais je ne penses pas que ça soit la solution optimale :euh: en ce qui concerne l'utilisation mémoire.

          Ma question est donc la suivante:
          Est-il possible, à la manière du FILE*, de créer un flux en tant que membre privé, et conserver ce flux en mémoire, sans avoir à le rappeler à chaque méthode? Si oui, comment?


          Merci d'avance ;)

          Edit: Voila le prototype de ma classe Ini_File, je n'ai pas encore corrigé toutes mes méthodes, ni les types requis aux paramètres, mais c'est pour montrer la structure:

          #include <iostream>
          #include <fstream>
          #include <string>

          using namespace std;

          class Ini_File
          {
          public:

          Ini_File(const char*);

          int Return_int();
          char Return_char();
          int GotoGroup(const char*);
          int GotoItem(const char*);

          void Display();
          const char* Return_dir();

          void OpenFile(const char*);
          void Analyse();
          void Insert_data(const char*, const char*, const char*);
          void GetAnalyse();

          ~Ini_File();

          private:

          string m_dir;
          fstream m_file;
          int n_char;
          int n_line;

          };


          Edit 2: Apparemment, je ne perds pas le flux, puisque après avoir désactivé une de mes méthodes "Analyse()", ça marche sans problème.
          Je dois donc corriger ma méthode fautive, probablement du au "while(m_file.eof())", qui est d'après ce que j'ai lu à éviter à tout prix, afin de ne pas avoir ce genre de bug.

          Bref mon souçi n'en est visiblement plus, alors merci encore pour ton aide ;)
          • Partager sur Facebook
          • Partager sur Twitter

          Fonctionnement étrange de fseek

          × Après avoir cliqué sur "Répondre" vous serez invité à vous connecter pour que votre message soit publié.
          × Attention, ce sujet est très ancien. Le déterrer n'est pas forcément approprié. Nous te conseillons de créer un nouveau sujet pour poser ta question.
          • Editeur
          • Markdown