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

Langage Delphi Discussion :

Comment lire un fichier séquentiel sans savoir ce qu'il contient ?


Sujet :

Langage Delphi

  1. #1
    Membre habitué

    Homme Profil pro
    Direction financière et formateur en gestion et contrôle de gestion
    Inscrit en
    Mai 2003
    Messages
    194
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 62
    Localisation : France, Haut Rhin (Alsace)

    Informations professionnelles :
    Activité : Direction financière et formateur en gestion et contrôle de gestion
    Secteur : Conseil

    Informations forums :
    Inscription : Mai 2003
    Messages : 194
    Points : 127
    Points
    127
    Par défaut Comment lire un fichier séquentiel sans savoir ce qu'il contient ?
    Bonjour à tous,
    Bon, aujourd'hui je m'attaque à un gros morceau (enfin pour moi).

    Le contexte :
    Je travaille avec des fichiers séquentiels contenant des champs strings, des booleans, des integers, et de floats.

    Le but:
    Lire le début du fichier mais de façon brute caractères par caractères, sans avoir à me soucier si ce que je lis est un string, un boolean ...

    Ce que j'ai fait :
    Lire les tutos sur les fichiers de Bodman et Frédéric Beaulieu et notamment la partie fichier binaire qui me semble répondre à la problématique

    Mais, il en ressort des signes assez kabbalistiques

    Je suis parti du code suivant de chez bodman:
    Code : 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
    23
    24
     
    procedure TForm1.Button1Click(Sender: TObject);
    var
       F:file;
       Buf: array[1..1] of Char;
       lus : integer;
    begin
        Button2.Tag:=0;
        Button3.Tag:=0;
        memo1.Clear;
     
        if opendialog1.execute then
        assignfile(f,opendialog1.filename);
        reset(F,1);
        repeat
              BlockRead(F, Buf, SizeOf(Buf),lus);
              memo1.lines.text := memo1.lines.text + buf+' ';
              Repeat
                    Application.ProcessMessages;
              Until Button2.Tag=1; // Button2 me permet d'avancer pas à pas (le clic sur ce bouton ne fait que mettre Button2.tag:=1)
              Button2.Tag:=0;
        until (lus =0) or (Button3.Tag=1); // Button3 me permet de mettre fin à la procédure
        closefile(F);
    end;
    J'ai lu les 10 premiers caractères
    et je sorts ça sur le memo1 :
    Nom : Capture1.JPG
Affichages : 388
Taille : 9,5 Ko

    alors qu'en consultant le fichier avec le bloc note j'ai ça
    Nom : Capture.JPG
Affichages : 412
Taille : 10,5 Ko

    Qu'est ce que j'ai mal fait et pas compris ?

  2. #2
    Rédacteur/Modérateur

    Avatar de SergioMaster
    Homme Profil pro
    Développeur informatique retraité
    Inscrit en
    Janvier 2007
    Messages
    15 202
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 68
    Localisation : France, Loire Atlantique (Pays de la Loire)

    Informations professionnelles :
    Activité : Développeur informatique retraité
    Secteur : Industrie

    Informations forums :
    Inscription : Janvier 2007
    Messages : 15 202
    Points : 41 443
    Points
    41 443
    Billets dans le blog
    63
    Par défaut
    Bonjour,
    Il manque juste une information : la version de Delphi ante ou post Unicode ?
    je pense qu'en remplaçant Char par AnsiChar tout va s'éclairer

  3. #3
    Expert éminent sénior
    Avatar de ShaiLeTroll
    Homme Profil pro
    Développeur C++\Delphi
    Inscrit en
    Juillet 2006
    Messages
    13 665
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 43
    Localisation : France, Seine Saint Denis (Île de France)

    Informations professionnelles :
    Activité : Développeur C++\Delphi
    Secteur : High Tech - Éditeur de logiciels

    Informations forums :
    Inscription : Juillet 2006
    Messages : 13 665
    Points : 25 459
    Points
    25 459
    Par défaut
    [1..1] of Char pourquoi pas directement un Char ?
    Si tu prévois de passer Buf en dynamique tu penseras à mettre Buf[1] comme paramètre à BlockRead


    D'ailleurs, tu peux lire un buffer de 1024 d'un coup et traiter un par un
    Entraine toi avec l'Hexadécimal aussi à la place comme dans ce sujet avec FileRead qui fonctionne comme BlockRead

  4. #4
    Membre habitué

    Homme Profil pro
    Direction financière et formateur en gestion et contrôle de gestion
    Inscrit en
    Mai 2003
    Messages
    194
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 62
    Localisation : France, Haut Rhin (Alsace)

    Informations professionnelles :
    Activité : Direction financière et formateur en gestion et contrôle de gestion
    Secteur : Conseil

    Informations forums :
    Inscription : Mai 2003
    Messages : 194
    Points : 127
    Points
    127
    Par défaut
    SergioMaster : Delphi postérieur à Unicode

    ShaiLeTroll : au début c'est ce que j'ai fait, mais j'ai toujours la même séquence de caractères en retour.
    Dans l'exemple il donnait bien
    Buf: array[1..1024] of Char;
    mais je me suis dit "comme je veux lire octet par octet" ... avec le même résultat

    Je me dit que ce qu'il lit ne correspond peut être pas à un caractère (et vu le résultat ...) alors comment faire ?

    Je viens de me pencher (mais pas trop au cas où ...) sur le code de ShaiLeTroll ... bon, il faut que je me penche un peu plus ...

  5. #5
    Membre confirmé
    Avatar de alheuredudejeuner
    Homme Profil pro
    Développeur informatique
    Inscrit en
    Août 2005
    Messages
    376
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France, Rhône (Rhône Alpes)

    Informations professionnelles :
    Activité : Développeur informatique
    Secteur : High Tech - Éditeur de logiciels

    Informations forums :
    Inscription : Août 2005
    Messages : 376
    Points : 632
    Points
    632
    Billets dans le blog
    4
    Par défaut C'est un problème de charset
    Bonjour,

    vous êtes sur la bonne piste.
    Ca ressemble à un problème de fichier fabriqué par le MainFrame avec des caractère particuliers au cobols.


    L'éditeur de texte interprète directement le fichier dans le bon encodage.

    En premier j'ouvrirai le fichier avec Notepad++ Par exemple et je regarderai son encodage(charset), (et afficher les caractère spéciaux)

    Je suivrai cette piste: http://docwiki.embarcadero.com/Libra...efaultEncoding


    Cordialement

  6. #6
    Membre habitué

    Homme Profil pro
    Direction financière et formateur en gestion et contrôle de gestion
    Inscrit en
    Mai 2003
    Messages
    194
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 62
    Localisation : France, Haut Rhin (Alsace)

    Informations professionnelles :
    Activité : Direction financière et formateur en gestion et contrôle de gestion
    Secteur : Conseil

    Informations forums :
    Inscription : Mai 2003
    Messages : 194
    Points : 127
    Points
    127
    Par défaut
    Bon j'ai triché!
    Ce fichier c'est moi qui l'est généré donc, en réalité, je sais exactement comment il est fait mais, voulant aller un peu plus loin je me suis imposé la condition de vouloir lire un fichier "inconnu"
    Du coup, je m'en suis sorti facilement avec ces lignes de code.
    Ca ne répond pas à mon interrogation mais ... ça fait le job dans ce cas là

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
     
    Var
       Fnt:file;
       oneByte:Byte;
       BtoStr:String;
       I:Integer;
    Begin
         BtoStr:='';
         Assignfile(Fnt,Fichier);
         Reset(Fnt,1);
         BlockRead(Fnt, oneByte, 1);   // Read one byte at a time
         for I := 1 to 25
         do BtoStr:=BtoStr+chr(oneByte);
         closefile(Fnt);
         ...
    En tout cas, merci à tous, et il y a du boulot pour comprendre les pistes données.

  7. #7
    Membre expert
    Avatar de Charly910
    Homme Profil pro
    Ingénieur TP
    Inscrit en
    Décembre 2006
    Messages
    2 405
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France

    Informations professionnelles :
    Activité : Ingénieur TP
    Secteur : Bâtiment Travaux Publics

    Informations forums :
    Inscription : Décembre 2006
    Messages : 2 405
    Points : 3 171
    Points
    3 171
    Par défaut
    Bonjour Patrice,

    je pense que le BlockRead doit être dans la boucle ?

    Code : 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
    procedure TForm1.Button2Click(Sender: TObject);
    Var
       Fnt:file;
       oneByte:Byte;
       BtoStr:String;
       I:Integer;
       Fichier : String ;
    Begin
      Fichier := E_Fichier.Text ;
      BtoStr:='';
      Assignfile(Fnt,Fichier);
      Reset(Fnt,1);
      For I := 1 to 25  do
        Begin
          BlockRead(Fnt, oneByte, 1);   // Read one byte at a time
          BtoStr:=BtoStr+chr(oneByte);
        End ;
      ShowMessage('Début du fichier '+ Fichier+Chr(13)+ BtoStr ) ;
      closefile(Fnt);
    end;
    Sinon tu peux aussi tester l'ouverture du fichier avant de le lire :

    Code : 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
    23
    24
    25
    26
    27
    28
    29
    30
    31
    32
    33
    procedure TForm1.Button3Click(Sender: TObject);
    var
      iFileHandle: Integer;
      iFileLength: Integer;
      iBytesRead: Integer;
      Buffer: PChar;
      i: Integer ;
      Fichier : String ;
      NbChar : Integer ;
      BtoStr : String ;
    begin
      Fichier := E_Fichier.Text ;
      iFileHandle := FileOpen(Fichier, fmOpenRead);
      If iFileHandle >0 Then
        Try
          iFileLength := FileSeek(iFileHandle,0,2);
          FileSeek(iFileHandle,0,0);
          Buffer := PChar(AllocMem(iFileLength + 1));
          iBytesRead := FileRead(iFileHandle, Buffer^, iFileLength);
          FileClose(iFileHandle);
          NbChar := Min(iBytesRead-1, 24) ;
          BtoStr:= '' ;
          for i := 0 to NbChar do
          begin
            BtoStr:=BtoStr+Buffer[i];
          end;
          ShowMessage('Début du fichier '+ Fichier+Chr(13)+ BtoStr ) ;
        Finally
          FreeMem(Buffer);
        End
      Else
        ShowMessage('Erreur d''ouverture du fichier '+Fichier) ;
    End;
    A+
    Charly

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

Discussions similaires

  1. Réponses: 5
    Dernier message: 27/08/2012, 19h02
  2. Librairie OpenSSL : comment lire une clef RSA sans fichier ?
    Par Feneck91 dans le forum Sécurité
    Réponses: 0
    Dernier message: 01/06/2012, 10h01
  3. [BCB 5]Comment lire un fichier AVI avec un TAnimate ?
    Par Sitting Bull dans le forum C++Builder
    Réponses: 2
    Dernier message: 15/09/2004, 11h57
  4. Comment lire un fichier DB en cours d'utilisation par 1 autr
    Par jbat dans le forum Bases de données
    Réponses: 4
    Dernier message: 12/03/2004, 11h06
  5. Comment lire un fichier image
    Par Charlemagne dans le forum DirectX
    Réponses: 9
    Dernier message: 12/03/2004, 00h22

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