Re: Stringverarbeitung - Leerzeichen reduzieren
Zitat:
|
Re: Stringverarbeitung - Leerzeichen reduzieren
Performancetuning, au fein...
Hatten wir mal :mrgreen: hier Hier die Version von Hawkeye219, die alles in den Schatten stellt.
Delphi-Quellcode:
function RemoveDoubleBlanks(const s: string): string;
var pRead, pEnd, pWrite : PChar; begin pRead := PChar(s); pEnd := pRead + Length(s); SetLength (Result, Length(s)); pWrite := PChar(Result); while (pRead <> pEnd) do begin repeat pWrite^ := pRead^; Inc (pRead); Inc (pWrite); until ((pRead[-1] = ' ') or (pRead = pEnd)); while (pRead^ = ' ') do Inc (pRead); end; SetLength (Result, pWrite - PChar(Result)); end; |
Re: Stringverarbeitung - Leerzeichen reduzieren
Uiii, hat sich ja ne Menge getan im Thread.
Danke allen für die vielen Vorschläge. Ich werde jeden einzelnen Vorschlag intensiv testen, leider erst wieder am Montag, über das Wochenende bin ich anderweitig voll beschäftigt. Die Zeiten der Performancetests werde ich natürlich hier posten. Wer mag kann ja noch weitere Vorschläge posten, ich werde auf jeden Fall jeden Vorschlag in den test einbeziehen. P.S.: @alzaimer, wäre es nicht besser wenigtens eine Prüfung mit pos() durchzuführen, um zu schauen, ob der Teilstring überhaupt vorkommt, bevor man den gesamten String Zeichen für Zeichen durchgeht? Aber auch diese Möglichkeit werde ich dann gleich mit testen. Danke allen für die rege Beteiligung. |
Re: Stringverarbeitung - Leerzeichen reduzieren
Zitat:
|
Re: Stringverarbeitung - Leerzeichen reduzieren
Guten Morgen zusammen,
ich habe alle Vorschläge quantitativ überprüft. Ich bin dabei folgendermassen vorgegangen. Ich habe eine Testapplikation erstellt, in der ich jede Funktion implementiert habe. Jede Funktion habe ich einzeln getestet, damit ich "Störeffekte" ausschliessen konnte. Auf einer Form befinden sich zwei TEdit´s ein TButton und ein TLabel. Der Teststring in unveränderter Form wird im ersten Edit angezeigt. Das Ergebnis aus der jeweiligen Funktion, nur zur Prüfung, ob die Funktion richtig läuft, in dem zweiten Edit. Der Knopf startet die Prüfung. Am Ende der Prüfung wird im Label die Zeit in ms die gebraucht wurde angezeigt. Ich habe zwei Teststrings benutzt einmal eine mit vielen Leerzeichen. Und für die zweite Prüfreihe einen String in der keine zwei Leerzeichen aufeinander folgen. In der Datenbank sind etwa 20% Strings die zwei oder mehr Leerzeichen, die aufeinander folgen enthalten. Für etwa 80% der Strings wird diese Funktion demnach nichts machen müssen. Jede Testreihe habe ich drei mal ausgeführt.
Delphi-Quellcode:
implementation
const C_TEST_STR = 'Dies ist ein Test. Hund Katze Maus Haus Garten Sonne'; C_TEST_NB = 'Dies ist ein Test. Hund Katze Maus Haus Garten Sonne'; function DeleteBlanksFromStr_A(const AString: string): string; begin ... end; ... function DeleteBlanksFromStr_G(const AString: string): string; begin ... end; procedure TForm1.Button1Click(Sender: TObject); const C_COUNT = 1000000; var LBegin, LEnd: int64; i: integer; begin Edit1.Text := C_TEST_NB; LBegin := GetTickCount; try for i := 1 to C_COUNT do begin Edit2.Text := DeleteBlanksFromStr_D(Edit1.Text); end; LEnd := GetTickCount; finally Label1.Caption := IntToStr(Lend- Lbegin); end; end; Hier die Ergebnisse: String mit zwei oder mehr aufeinanderfolgenden Leerzeichen. Tyrael Y: 26313 / 26360 / 26328 jfheins : 18656 / 18860 / 18547 nahpets : 23359 / 23344 / 23360 Sir Rufo: 91390 / 91360 / 91219 DeddyH : 18563 / 18547 / 18484 alzaimer_1: 18031 / 18062 / 17969 alzaimer_2: 17953 / 17860 / 17922 String ohne zwei oder mehr aufeinanderfolgenden Leerzeichen. Tyrael Y: 17750 / 17578 / 17656 jfheins : 17547 / 17469 / 17531 nahpets : 17344 / 17297 / 17391 Sir Rufo: 17125 / 17016 / 17156 DeddyH : 17844 / 17859 / 17843 alzaimer_1: 17484 / 17687 / 17453 alzaimer_2: 17031 / 17062 / 17047 alzaimer_2 ist folgende Ergänzung zum Ursprungscode
Delphi-Quellcode:
function DeleteBlanksFromStr_G(const s: string): string;
var pRead, pEnd, pWrite : PChar; begin if Pos(' ', s) > 0 then begin pRead := PChar(s); pEnd := pRead + Length(s); SetLength (Result, Length(s)); pWrite := PChar(Result); while (pRead <> pEnd) do begin repeat pWrite^ := pRead^; Inc (pRead); Inc (pWrite); until ((pRead[-1] = ' ') or (pRead = pEnd)); while (pRead^ = ' ') do Inc (pRead); end; SetLength (Result, pWrite - PChar(Result)); end else begin result := s; end; end; Die zusätzliche Prüfung mit Pos scheint nicht wirklich einen großen Unterschied zu machen. Letzendlich ist es aber über alle Versuche gesehen in allen Fällen die schnellste Variante. Diese Variante werde ich jetzt auch einsetzen. Danke allen nochmal für die rege Beteiligung. |
Alle Zeitangaben in WEZ +1. Es ist jetzt 20:33 Uhr. |
Powered by vBulletin® Copyright ©2000 - 2024, Jelsoft Enterprises Ltd.
LinkBacks Enabled by vBSEO © 2011, Crawlability, Inc.
Delphi-PRAXiS (c) 2002 - 2023 by Daniel R. Wolf, 2024 by Thomas Breitkreuz