Einzelnen Beitrag anzeigen

Benutzerbild von Zacherl
Zacherl

Registriert seit: 3. Sep 2004
4.629 Beiträge
 
Delphi 10.2 Tokyo Starter
 
#4

AW: MyGetAverageWordLengthFromFile

  Alt 20. Apr 2016, 13:28
Komm schon .. du bist doch lange genug dabei, um zu wissen, dass man seine Posts 24h lang editieren kann

Variante für nicht-Dateien:
Delphi-Quellcode:
function AvgWordLength(const Text: String): Single;
var
  I: Integer;
  B: Boolean;
  TotalWordCount,
  TotalWordLength: UInt64;
begin
  Result := 0;
  B := false;
  TotalWordCount := 0;
  TotalWordLength := 0;
  for I := Low(Text) to High(Text) do
  begin
    if (not CharInSet(Text[I], [#00..#32, ',', ';', '.', ':'])) then
    begin
      if (not B) then
      begin
        B := true;
        Inc(TotalWordCount);
      end;
      Inc(TotalWordLength);
    end else
    begin
      B := false;
    end;
  end;
  if (TotalWordCount <> 0) then
  begin
    Result := TotalWordLength / TotalWordCount;
  end;
end;
Inklusive folgender Modifikationen:
  1. CharInSet für Unicode Support
  2. UInt64 statt Integer für Strings > 2GiB (sicher ist sicher )

Hier noch meine Version für Dateien:
Delphi-Quellcode:
function AvgWordLength(const Filename: String; MaxLength: UInt64 = 0): Single;
const
  BUFFERSIZE = 1024 * 16;
var
  FS: TFileStream;
  Buffer: array[0..BUFFERSIZE - 1] of AnsiChar; // Replace with AnsiChar for non-unicode files
  BytesRead,
  I: Integer;
  B: Boolean;
  TotalWordCount,
  TotalWordLength: UInt64;
begin
  Result := 0;
  FS := TFileStream.Create(Filename, fmOpenRead);
  try
    B := false;
    TotalWordCount := 0;
    TotalWordLength := 0;
    while (FS.Position < FS.Size) and ((MaxLength = 0) or (FS.Position < MaxLength)) do
    begin
      BytesRead := FS.Read(Buffer[0], BUFFERSIZE * SizeOf(Buffer[0]));
      for I := 0 to BytesRead div SizeOf(Buffer[0]) - 1 do
      begin
        if (not CharInSet(Buffer[I], [#00..#32, ',', ';', '.', ':'])) then
        begin
          if (not B) then
          begin
            B := true;
            Inc(TotalWordCount);
          end;
          Inc(TotalWordLength);
        end else
        begin
          B := false;
        end;
      end;
    end;
  finally
    FS.Free;
  end;
  if (TotalWordCount <> 0) then
  begin
    Result := TotalWordLength / TotalWordCount;
  end;
end;
Inklusive folgender Modifikationen:
  1. Liest Datei Blockweise statt Byteweise aus (stark erhöhte Performance)
Projekte:
- GitHub (Profil, zyantific)
- zYan Disassembler Engine ( Zydis Online, Zydis GitHub)

Geändert von Zacherl (20. Apr 2016 um 14:47 Uhr)
  Mit Zitat antworten Zitat