Cours utilisation des fichiers typés sous Delphi 8, tutoriel & guide de travaux pratiques Delphi en pdf.
Accéder au fichier typé
Ce paragraphe va présenter l’accès à un fichier typé dont les éléments sont du type suivant :
Type
TElement=Packed Record
eleEntier : Integer;
eleReel : Double;
eleChaine : String[100];
End;
Création de la classe TFileElement
Pour accéder au fichier contenant des TElements, nous allons créer une classe descendante de TFileRecord nommée TFileElement. L’unité UFileRecord n’a pas besoin d’être modifiée et peut donc être ajoutée telle quelle à votre projet.
Cette classe doit ressembler à la déclaration suivante :
Type
TFileElement=Class(TFileRecord)
Public
Constructor Create;
Procedure Read(Var Element:TElement);
Procedure Write(Const Element:TElement);
End;
La surcharge du constructeur est obligatoire afin de préciser la taille d’un élément du fichier. les deux autres méthodes sont ici pour la lecture et l’écriture des enregistrements.
Surcharge du constructeur
La surcharge du constructeur sera la suivante dans le cas ou la taille de l’enregistrement est connue :
constructor TFileElement.Create;
begin
inherited;
Taille:=113;
end;
A noter que la taille de l’élément doit être spécifiée directement. La fonction SizeOf ne retourne plus la valeur correcte sous Delphi 8. La valeur peut être obtenue par l’utilisation de SizeOf sous Delphi 7.
Une autre solution est de créer un fichier temporaire d’un élément dans le constructeur et d’en obtenir la taille. Cette solution sera préférable dans le cas ou la taille n’est pas connue, ou que la structure du fichier sera amenée à être modifiée par la suite.
constructor TFileElement.Create;
Var Element:TElement;
begin
inherited;
AssignFile(ExtractFilePath(Application.ExeName)+’~temp.dat’);
Rewrite;
Write(Element);
Taille:=Stream.Size;
CloseFile;
AssignFile( »);
DeleteFile(ExtractFilePath(Application.ExeName)+’~temp.dat’);
end;
Remarque, dans le cas ou vous n’utilisez pas les méthode TFileRecord.FileSize ou TFileRecord.Seek ( avec une valeur non nulle ), la taille de l’enregistrement n’est pas utile. Dans ce cas elle peut être fixée à 1 quelle que soit la taille réelle de l’enregistrement.
Méthodes de lecture et d’écriture d’un élément
Il faut ensuite construire les méthodes de lecture et d’écriture d’un élément. Comme la lecture globale n’est plus autorisée, les champs seront lus un par un dans l’ordre du Record.
Dans notre exemple les méthode de lecture et d’écriture seront les suivantes :
procedure TFileElement.Read(var Element: TElement);
begin
If Assigned(Stream) Then
Begin
Stream.Read(Element.eleEntier);
Stream.Read(Element.eleReel);
ReadShortString(Element.eleChaine,High(Element.eleChaine));
End;
end;
procedure TFileElement.Write(const Element: TElement); begin
If Assigned(Stream) Then
Begin
Stream.Write(Element.eleEntier); Stream.Write(Element.eleReel); WriteShortString(Element.eleChaine,High(Element.eleChaine));
End;
end;
ATTENTION : dans l’exemple donné ici le Record est de type Packed, dans le cas contraire, il peut y avoir des octets inutilisés d’alignement entre les champs. Il faut donc lire et écrire ces octets intermédiaires.
Le code suivant donne un exemple d’ajout de la lecture d’un octet d’alignement dans le flux. Il n’y a pas malheureusement de règle simple pour connaitre où sont les octets d’alignement car Delphi 1, Delphi 2, Delphi 3/4, Delphi 5/6/7 donnais des résultats différents sur chaque version.
procedure TFileUnAutreElement.Read(var UnAutreElement: TUnAutreElement);
Var Octet:Byte;
begin
If Assigned(Stream) Then
Begin
Stream.Read(UnAutreElement.eleEntier);
Stream.Read(UnAutreElement.eleReel);
Stream.Read(octet); // Lecture d’un octet d’alignement. ReadShortString(eleChaine,High(UnAutreElement.eleChaine));
End;
end;
Exemple de lecture séquentielle d’un fichier
Sous Delphi 7 la méthode suivante de parcours complet d’un fichier pour remplir un tableau ou une autre structure est fréquente :
code Delphi 7
procedure TForm1.btnLireClick(Sender: TObject);
Var Fichier:File Of TElement;
Element:TElement;
begin
AssignFile(Fichier, ExtractFilePath(Application.ExeName)+’fichier.dat’);
code Delphi 7
Reset(Fichier);
Try
Liste.Clear;
While Not Eof(Fichier) Do
Begin
Read(Fichier,Element);
With Liste.Items.Add Do
Begin
Caption := Element.eleChaine;
SubItems.Add(IntToStr(Element.eleEntier));
SubItems.Add(Format(‘%1.3f’,[Element.eleReel]));
End;
End;
Finally
CloseFile(Fichier);
end;
end;
La classe TFileElement va permettre de conserver la structure du code en créant une instance de la classe. Après la création de la classe, les anciens appels de procédures seront simplement remplacés par les appels des méthodes de même nom de la classe.
code Delphi 8
procedure TForm1.btnLireClick(Sender: TObject);
Var Fichier:TFileElement;
Element:TElement;
begin
Fichier:=TFileElement.Create;
Try
Fichier.AssignFile(ExtractFilePath(Application.ExeName)+’fichier.dat’);
Fichier.Reset;
Liste.Clear;
While Not Fichier.EOF Do
Begin
Fichier.Read(Element);
With Liste.Items.Add Do
Begin
Caption := Element.eleChaine;
SubItems.Add(IntToStr(Element.eleEntier));
SubItems.Add(Format(‘%1.3f’,[Element.eleReel]));
End;
End;
Finally
Fichier.CloseFile;
Fichier.Free;
end;
end;
Introduction
I – Classe TFileRecord
I-A – Pourquoi créer cette nouvelle classe ?
I-B – Description de la classe TFileRecord
II – Accéder au fichier typé
II-A – Création de la classe TFileElement
II-B – Surcharge du constructeur
II-C – Méthodes de lecture et d’écriture d’un élément
II-D – Exemple de lecture séquentielle d’un fichier
II-E – Acces direct à un élément
Conclusion
……….