Jump to content
ginnix

Saving records

Recommended Posts

Hi All,

 

I  have this record Type

 type
   TCustomer= record
     CompanyName:String[255];
     SpotsAllocated:Integer;
     LicensePlates:String[255];
     Parked:string[255];
   end;
   var
   myFile:File of TCustomer;
   CompanyDataBase:array[1..100] of TCustomer;
 

 

 

 

To save the information once the record is populated I use

AssignFile(F, 'c:\tmp\test.txt');
  Rewrite(F);
  for i := Low(CompanyDataBase) to High(CompanyDataBase) do
   Write(F, CompanyDataBase);
   CloseFile(F);

 

This seems to work, I can see the data in the text file.  

 

My problem is reading this back. I am stuck on how to read the data back into the program.

 

 

Any tips appreciated.

 

Thanks

 

 

 

 

Share this post


Link to post

Hello,

This is a very old school way of saving data. Probably from Pascal in 1980. You should not do it this way any longer. I would do something as follows (note, I am writing this without testing syntax)


 

TCustomer= record
     CompanyName:String[255];
     SpotsAllocated:Integer;
     LicensePlates:String[255];
     Parked:string[255];
     procedure SaveToStream(aStream:TStream);
     procedure LoadFromStream(aStream:TStream)
   end;


TCustomerArr=array of TCustomer;

TCustomerArrHelper=record helper for TCustomerArr
  procedure SaveToStream(aStream:TStream)
  procedure LoadFromSTream(aSTream:TStream)
  procedure SaveToFile(const aFileName:string);

end;


procedure TCustomer.SaveToSTream(aStream:TStream);
var
  ver:integer;
begin
   ver:=1; // always save a version number in case you change the record format in the future
   aStream.WriteBuffer(ver,sizeof(ver));
  // call aStream.Write for other fields

end;

procedure TCustomer.LoadFromSTream(aStream:TStream);
var
   ver:integer;
begin
   aStream.ReadBuffer(ver,sizeof(ver));
  if ver<>1 then raise Exception.Craete('Version mismatch');
  aSTream.ReadBuffer();// one readbuffer to match the writes above
end;


procedure TCustomerArrHelper.SaveToStream(aStream:TSTream);
var
  ver:integer;
  cust:TCustomer;
begin
   ver:=1;
   aStream.WriteBuffer(ver,sizeof(ver));
   myLen:=Length(self);
   sTream.WriteBuffer(myLen,sizeof(mylen)); // save the length, you will use the length when reading in to allocate the array size
   for cust in self do
      cust.SaveToSTream(aStream);
end



procedure TCustomerArrHelper.LoadFromStream(aStream:TSTream);
var
  ver:integer;
  myLen:integer;
  cust:TCustomer;
begin

   aStream.ReadBuffer(ver,sizeof(ver));
   if ver<>1 then raise Exception.Craete('Version mismatch');

   aSTream.ReadBuffer(myLen,sizeof(mylen));
   SetLength(self,myLen)

   for cust in self do
      cust.LoadFromSTream(aStream);
end


procedure TCustomerArrHelper.SaveToFile(const aFileName:string);
var
  f:TFileStream;
begin
  f:=TFileStream.Create(aFileName,fmCreate);
  try
    someCustArr.SaveToSTream(f);
  finally
    f.free
  end
end

 

 

 

Edited by Dave Novo

Share this post


Link to post
13 hours ago, ginnix said:

AssignFile(F, 'c:\tmp\test.txt');
  Rewrite(F);
  for i := Low(CompanyDataBase) to High(CompanyDataBase) do
   Write(F, CompanyDataBase);
   CloseFile(F);

Have you tried the obvious:

AssignFile(F, 'c:\tmp\test.txt');
Reset(F);
for i := Low(CompanyDataBase) to High(CompanyDataBase) do
   Read(F, CompanyDataBase[I]);
CloseFile(F); 

 

Share this post


Link to post
39 minutes ago, PeterBelow said:

for i := Low(CompanyDataBase) to High(CompanyDataBase) do

As far as I remember this should be

 

i:=0;

SetLength(CompanyDataBase, FileSize(f))

while not eof(f) do

begin

  Read(f, CompanyDataBase);

  inc(i);

end;

 

Last time I wrote a code like this was in Pascal. (Btw. to be on the safe side you should also define the record as packed).

Share this post


Link to post

Create an account or sign in to comment

You need to be a member in order to leave a comment

Create an account

Sign up for a new account in our community. It's easy!

Register a new account

Sign in

Already have an account? Sign in here.

Sign In Now

×