Einzelnen Beitrag anzeigen

Benutzerbild von olee
olee

Registriert seit: 16. Feb 2008
Ort: Boppard
540 Beiträge
 
Turbo Delphi für Win32
 
#1

WideSameText und co. sehr langsam!

  Alt 28. Aug 2011, 17:46
Delphi-Version: 2006
Hallo alle zusammen!

Ich habe mich in letzter Zeit etwas mit WideStrings in Turbo Delphi beschäftigt und dabei festgestellt, dass die Utility-Funktionen für diese verdammt lahm sind.

Als ich der Sache nachgegangen bin ist mir auch schon schnell aufgefallen wieso:
Diese Funktionen rufen teilweise extra Windows-Funktionen auf!
So z.B. bei WideSameText welches intern CompareStringW aus der kernel32.dll aufruft.

Deshalb habe ich mich mal daran gemacht native alternativen für diese Methoden zu schreiben.
Diese erwiesen sich im Test mehr als das 4-fach so schnell sind wie die Originale aus der SysUtils unit.

Hier der Code:
Delphi-Quellcode:
// FASTER version of WideSameStr
function WideSameStr(const a,b: WideString): Boolean;
var
  ac, bc : PWideChar;
label
  ende_false, ende_true;
begin
// If Pointer(a) = Pointer(b) then
// begin
// Result := true;
// exit;
// end;
// If (length(a) <> length(b)) then
// begin
// Result := false;
// exit;
// end;
// If (length(a) = 0) then
// begin
// Result := true;
// exit;
// end;
  asm
    cmp eax, edx // a = b
    jz ende_true // --> return true
    test eax, eax // a = nil
    jz ende_false // --> return false

    mov ecx, [eax-$04]
    test ecx, ecx // length(a) = 0
    jz ende_false // --> return false
    cmp ecx, [edx-$04] // length(a) <> length(b)
    jz ende_true // --> return false
  end;
ende_false:
  Result := false;
  exit;
ende_true:

  ac := @a[1];
  bc := @b[1];
  repeat
    if ac^ <> bc^ then
    begin
      Result := false;
      exit;
    end;
    inc(ac);
    inc(bc);
  until ac^ = #0;
  Result := true;
end;

// FASTER version of WideSameText
function WideSameText(const a,b: WideString): Boolean;
var
  ac, bc : PWideChar;
label
  ende_false, ende_true;
begin
// If Pointer(a) = Pointer(b) then
// begin
// Result := true;
// exit;
// end;
// If (length(a) <> length(b)) then
// begin
// Result := false;
// exit;
// end;
// If (length(a) = 0) then
// begin
// Result := true;
// exit;
// end;
  asm
    cmp eax, edx // a = b
    jz ende_true // --> return true
    test eax, eax // a = nil
    jz ende_false // --> return false

    mov ecx, [eax-$04]
    test ecx, ecx // length(a) = 0
    jz ende_false // --> return false
    cmp ecx, [edx-$04] // length(a) <> length(b)
    jz ende_true // --> return false
  end;
ende_false:
  Result := false;
  exit;
ende_true:

  ac := @a[1];
  bc := @b[1];
  repeat
    if WideUpCase(ac^) <> WideUpCase(bc^) then
    begin
      Result := false;
      exit;
    end;
    inc(ac);
    inc(bc);
  until ac^ = #0;

  Result := true;
end;
Mit freundlichen Grüßen
Björn Zeutzheim
Björn Zeutzheim
Codename: Performancepumpe
  Mit Zitat antworten Zitat