Strings schnell auf Ähnlichkeit überprüfen
Hi,
ich muss in einer ListView doppelte und ähnliche Eintrage finden und hab das mit dem Levenshtein Algorithmus aus der Code Library versucht, klappt ja ganz vorzüglich, nur leider VIEL zu langsam. Eine Listview enthält entweder komplett nur PlainText zum vergleichen, z.B. Zitat:
Zitat:
Weiß da jemand eine Lösung? |
Re: Strings schnell auf Ähnlichkeit überprüfen
Das ist auch das langsamste, was Du da hast:
Zitat: Zitat:
Such mal unter Google nach folgenden Begriffen: "Similarity String Joins q-grams" Fertigen Delphi Code wirst Du da aber wahrscheinlich nicht finden, bleibt oft nur die Arbeit, eventuell C Quellen nach Delphi zu portieren. Gruß stoxx |
Re: Strings schnell auf Ähnlichkeit überprüfen
Glaub das is zu hoch für mich, aber könnte man nicht beim ersten String alle Wörter anhand des Trennzeichens ' ' zählen und dann diese im zweiten String suchen und je nachdem wieviele gefunden werden, das Prozentual ausrechnen?! Wird zwar nicht genau sein, aber für meine Zwecke sollte es reichen.
|
Re: Strings schnell auf Ähnlichkeit überprüfen
Zitat:
|
Re: Strings schnell auf Ähnlichkeit überprüfen
Ja hab ich, habs auch versucht aber irgendwie net hinbekommen.
Delphi-Quellcode:
procedure TfrmMain.Button1Click(Sender: TObject);
var i, a, Minimum, Maximum, Distance, MaxDistance, LengthFirstString, LengthSecondString: Integer; begin MaxDistance := 15; For i := 0 to lstRSSData.Items.Count - 1 do begin LengthFirstString := Length(lstRSSData.Items.Item[i].SubItems.Strings[3]); Minimum := LengthFirstString - (MaxDistance * LengthFirstString div 100); Maximum := LengthFirstString + (MaxDistance * LengthFirstString div 100); For a := i to lstRSSData.Items.Count - 1 do If a <> i then begin LengthSecondString := Length(lstRSSData.Items.Item[a].SubItems.Strings[3]); If (LengthSecondString >= Minimum) and (LengthSecondString <= Maximum) then begin // ShowMessage(IntToStr(LengthFirstString) + #13#10 + IntToStr(temp1) + // #13#10 + IntToStr(temp2)); distance := Levenshtein(lstRSSData.Items.Item[i].SubItems.Strings[3], lstRSSData.Items.Item[a].SubItems.Strings[3]); If distance <= maxdistance then ShowMessage('Duplicate text found!' + #13#10#13#10 + 'i' + IntToStr(i) + ': ' + #13#10 + lstRSSData.Items.Item[i].SubItems.Strings[2] + #13#10#13#10 + 'a' + IntToStr(a) + ': ' + #13#10 + lstRSSData.Items.Item[a].SubItems.Strings[2] + #13#10#13#10 + 'Difference: ' + IntToStr(distance) + ' %'); end; end; end; end; |
Re: Strings schnell auf Ähnlichkeit überprüfen
Was genau funktioniert denn da nicht? Sieht doch schon ganz gut aus.
Ein paar Kommentare: 15% Abweichung ist eine Welt. Das sind bei Längen von 1.000-15.000 Zeichen bis zu 150-2.250 unterschiedliche Zeichen. Vielleicht solltest du die Toleranzgrenze heruntersetzen, dafür aber die Strings vorher `glätten´ (HTML Markup entfernen, nur Kleinschreibung, alle Leer- und Interpunktionszeichen durch ein einziges Leerzeichen ersetzen, usw.) Der Zugriff über Subitems.Strings[3] ist wohl nicht der schnellste. Eventuell solltest du die Strings vorher in ein TStringList kopieren. Wenn du aber wirklich nur ca. 50 Einträge hast, dann wird sich das wohl nicht lohnen. |
Re: Strings schnell auf Ähnlichkeit überprüfen
Zitat:
Zitat:
Zitat:
|
Alle Zeitangaben in WEZ +1. Es ist jetzt 20:08 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