Autor Beitrag
bjrtap26
Hält's aus hier
Beiträge: 1



BeitragVerfasst: Do 24.03.11 10:09 
Hallo!

Ich habe eine Datei mit Text, in diese Datei wird laufend neuer Text geschrieben von einem anderen Programm.
Nun möchte ich mit meiner App auf diese Datei lesend zugreifen, und jedesmal wenn eine Zeile dazukommt, diese auswerten. Das entspricht ziemlich genau dem Tail -f unter linux.

Ich habe bereits eine Lösung (dieses Parsen der Datei läuft in einem eigenen Thread):

ausblenden volle Höhe Delphi-Quelltext
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:
34:
35:
36:
37:
38:
39:
40:
41:
42:
43:
44:
45:
procedure TParseThread.execute;
var AHStream : THandleStream;
    AFileHandle : THandle;
    str, nstr: string;
    buf: TBytes;
    enc: TEncoding;
    LOffset: Integer;
    s: int64;
begin
  if not FileExists(pfile) then  Exit;

  AFileHandle := CreateFile(PChar(pfile), GENERIC_READ, FILE_SHARE_READ or FILE_SHARE_WRITE, nil, OPEN_EXISTING, FILE_ATTRIBUTE_NORMAL, 0);

  if AFileHandle <> INVALID_HANDLE_VALUE then begin
    AHStream := THandleStream.Create(AFileHandle);

    s := ahstream.Size;
    enc:= nil;
    setlength(buf, s);
    ahstream.ReadBuffer(Pointer(buf)^, s);
    LOffset := TEncoding.GetBufferEncoding(buf, enc);
    str := enc.GetString(buf, loffset, s-loffset);

    str := '';
    repeat
      while ahstream.Position = ahstream.Size do application.ProcessMessages;
      sleep(10);

      setlength(buf, 1);
      ahstream.ReadBuffer(pointer(buf)^, 1);
      nstr := enc.GetString(buf, 01);
      if nstr <> #10 then str :=  str + nstr;
      if nstr = #13 then begin

        // HIER PARSEN
        parse(str);

        str := '';
      end;
    until false;

    FreeAndNil(AHStream);
    CloseHandle(AFileHandle);
  end;
end;



Wie ihr seht sehr unelegant, ich habe busy waiting drin und lese immer nur ein Zeichen...

Das muss doch besser gehen!
Wie gesagt ich brauche immer ganze Zeilen zum auswerten für meinen Parser.

Jemand ne Idee?
Gruß
B

Moderiert von user profile iconMartok: Code- durch Delphi-Tags ersetzt
jaenicke
ontopic starontopic starontopic starontopic starontopic starontopic starontopic starofftopic star
Beiträge: 19315
Erhaltene Danke: 1747

W11 x64 (Chrome, Edge)
Delphi 11 Pro, Oxygene, C# (VS 2022), JS/HTML, Java (NB), PHP, Lazarus
BeitragVerfasst: Do 24.03.11 11:13 
Hallo und :welcome:

Also erstens nimm das Application.ProcessMessages raus...
Das ist dafür, dass z.B. die GUI nicht hängt, weil die Messages nicht abgearbeitet werden. Ein Thread ist aber genau dafür da, dass er eben nebenbei läuft. Da ist das Sleep statt Application.ProcessMessages schon korrekt.

Zweitens kannst du dich über Änderungen an Dateien informieren lassen:
msdn.microsoft.com/e...365261(v=vs.85).aspx

Je nach Anwendung kann es auch Sinn machen schlicht WriteFile zu hooken und so jeden Schreibvorgang direkt mitzubekommen.