String in typisierter Datei (typed binary) speichern

Für Fragen zur Programmiersprache auf welcher Lazarus aufbaut

String in typisierter Datei (typed binary) speichern

Beitragvon ConcAPPtLab » 28. Sep 2017, 21:29 String in typisierter Datei (typed binary) speichern

Hallo,

ich möchte eine Liste von Objekten in einer typisierten Datei speichern. Ein Objekt hat natürlich einen Namen (hier: fTitle/Title). Allerdings habe ich Probleme, diesen korrekt zu speichern und wieder auszulesen. Nach einer Weile und einigen unsauberen Tricks habe ich es geschafft, den String zumindest ohne Laufzeitfehler abzuspeichern. Allerdings wird beim Ausleseversuch mit einem SIGSEV-Fehler abgebrochen und beim Rantasten mit Debugger wahlweise eine Zeichenfolge mit diversen Steuerzeichen oder aber ein Hinweis á la "uncomparsed character" oder so angezeigt.

Definition der wichtigen Klassen:
Code: Alles auswählen
{ TSession }
TSession = class(TTimer)
    private
      { unwichtig (weitere Zeitstempel) }
      fMemDur: TDateTime;
      fTitle: string[50];
 
      function getTitle(): string;
 
    public
      { unwichtig (Konstruktor und weitere Prozeduren) }
      function getDuration(): TDateTime;
 
    { unwichtig (weitere Properties) }
    property memDur: TDateTime read fMemDur;
    property Title: string read getTitle;
  end;
 
{ TSessFile }
 
  TSessFile = file of TSession;
 
{ TSessionList }
 
  TSessionList = class
    private
      fSessionFile: TSessFile;
 
      fActiveSession: integer;
      fFilePath: string;
      fSessions: array of TSession;
 
      function getSession(id: integer): TSession;
      procedure setSession(id: integer; session: TSession);
 
      procedure load();
      procedure save();
 
    public
      { unwichtig (Konstruktor und weitere Prozeduren) }
 
    { unwichtig (Properties) }
  end;
 
var list: TSessionList;


Angegebene Funktionen:
Code: Alles auswählen
function TSession.getTitle(): string;
begin
  result := fTitle;
end;
 
function TSession.getDuration(): TDateTime;
begin
 
  { calculate new memory Duration }
 
    result := fMemDur + (Now() - fStartStamp);
 
end;


Laden und Speichern der Liste:
Code: Alles auswählen
procedure TSessionList.load();
var memSession: TSession;
    i: integer;
begin
 
  closeSessions();    // close all sessions
 
  assignFile(fSessionFile, fFilePath);
 
  if not DirPathExists(ExtractFilePath(fFilePath)) then
    CreateDir(ExtractFilePath(fFilePath));
 
  if fileExists(fFilePath) then
    reset(fSessionFile)
  else
    rewrite(fSessionFile);
 
  { read file content }
 
  SetLength(fSessions, fileSize(fSessionFile));
  i := 0;
 
  while not ((eof(fSessionFile)) or (i = length(fSessions)))  do
    begin
 
      Read(fSessionFile, memSession);
 
      fSessions[i] := memSession;
 
      Inc(i);
 
    end;
 
  closeFile(fSessionFile);
 
end;
 
procedure TSessionList.save();
var i: integer;
    memSession: TSession;
begin
 
  assignFile(fSessionFile, fFilePath);
  rewrite(fSessionFile);
 
  i := 0;
 
  while not (i = length(fSessions))  do
    begin
 
      memSession := fSessions[i];
 
      Write(fSessionFile, memSession);
 
      Inc(i);
 
    end;
 
  closeFile(fSessionFile);
 
end


Anzeige des Dateiinhalts:
Code: Alles auswählen
msg := '';
 
  for i:=0 to list.count-1 do
    begin
      msg := msg + 'Name: ' + list.sessions[i].Title + #13#10 +
      'Dauer: ' + FormatDateTime('hh:mm:ss', list.sessions[i].getDuration()) +
      #13#10#13#10;
    end;
 
  ShowMessage(msg);


Ich nehme an, dass das Ganze etwas damit zu tun hat, dass Strings eigentlich nicht zu den einfachen Datentypen zählen und nicht immer ohne weiteres in einer Datei gespeichert werden können. Das komische ist halt nur, dass ich so etwas in der Art nicht gerade zum ersten Mal mache.
Aber sei's drum, ich hoffe einfach Mal, dass jemand von Euch eine Lösung findet :)

LG
ConcApptLab
Definition "Strategische Fehlerkorrektur":
Solange rumprobieren bisses klappt :D
ConcAPPtLab
 
Beiträge: 82
Registriert: 18. Apr 2014, 17:57

Beitragvon Mathias » 28. Sep 2017, 21:43 Re: String in typisierter Datei (typed binary) speichern

Code: Alles auswählen
type
TSession = class(TTimer)
    private
.....
var
  TSessFile = file of TSession;

Willst du die ganze Klasse abspeichern ?
Mit Lazarus sehe ich gün
Mit Java und C/C++ sehe ich rot
Mathias
 
Beiträge: 3249
Registriert: 2. Jan 2014, 17:21
Wohnort: Schweiz
OS, Lazarus, FPC: Linux (die neusten Trunc) | 
CPU-Target: 64Bit
Nach oben

Beitragvon braunbär » 28. Sep 2017, 23:42 Re: String in typisierter Datei (typed binary) speichern

Ich wäre nie auf die Idee gekommen, ein File of class zu erstellen, und ich glaube auch nicht, dass das eine gute Idee ist.
Aber ein
Code: Alles auswählen
Read(fSessionFile, memSession);
ohne vorher Speicher für memsession anzulegen
Code: Alles auswählen
memsession:=Tsession.create
kann nur schiefgehen.
braunbär
 
Beiträge: 164
Registriert: 8. Jun 2017, 17:21

Beitragvon ConcAPPtLab » 28. Sep 2017, 23:53 Re: String in typisierter Datei (typed binary) speichern

Ohh Mann, vielen Dank euch beiden. Meine Lazarus-Kenntnisse sind echt eingerostet!
Werde jetzt erst einmal ein Record mit den zu speichernden Daten definieren und diese dann in der Datei speichern.

Schäme mich gerade so sehr ... XD
Definition "Strategische Fehlerkorrektur":
Solange rumprobieren bisses klappt :D
ConcAPPtLab
 
Beiträge: 82
Registriert: 18. Apr 2014, 17:57

• Themenende •

Zurück zu Freepascal



Wer ist online?

Mitglieder in diesem Forum: 0 Mitglieder und 3 Gäste

porpoises-institution
accuracy-worried