![]() |
TListView Duplikate rückwärts löschen
Könnte mir jemand helfen diese Prozedur zum laufen zu bekommen? Es soll von allen doppelten Einträgen immer nur das unterste Item übrigbleiben. Hab schon länger rumprobiert bekomm aber immer nen "out of bounds" Fehler, sollte wohl andersrum anfangen also bei lv.items.count - 1 und vielleicht wär ne for schleife auch besser aber irgendwie krieg ichs grad net hin.
Delphi-Quellcode:
procedure DeleteFirstDoubles(lv: TListView; SubItem: integer = -1);
var li1 : TListItem; li2 : TListItem; x : integer; y : integer; begin if lv.Items.Count < 1 then Exit; x := 0; while x <= lv.Items.Count - 1 do begin li1 := lv.Items[x]; y := x + 1; while y <= lv.Items.Count - 1 do begin li2 := lv.Items[y]; if SubItem > -1 then begin if AnsiSameText(li1.SubItems[SubItem], li2.SubItems[SubItem]) then li1.Delete; end else begin if AnsiSameText(li1.Caption, li2.Caption) then li1.Delete; end; inc(y); end; inc(x); end; end; |
Re: TListView Duplikate rückwärts löschen
ich habs mal so geändert, dass es funktioniert (ansiCompareText nur, weil AnsiSameText in D3 nicht existiert)
das ganze ist jetzt rückwärts...
Delphi-Quellcode:
Gruß Frank
procedure DeleteFirstDoubles(lv: TListView; SubItem: integer);
var li1,li2: TListItem; x,y : integer; begin if lv.Items.Count < 1 then Exit; x := lv.Items.Count - 1; while x >= 1 do begin li1 := lv.Items[x]; y := x - 1; while y >= 0 do begin li2 := lv.Items[y]; if SubItem > -1 then begin if AnsiCompareText(li1.SubItems[SubItem], li2.SubItems[SubItem])=0 then li2.Delete; end else begin if AnsiCompareText(li1.Caption, li2.Caption)=0 then li2.Delete; end; dec(y); end; dec(x); end; end; |
Re: TListView Duplikate rückwärts löschen
Guten Morgen,
hier noch eine tageslichttaugliche Alternative:
Delphi-Quellcode:
Grüße vom marabu
procedure RemoveDuplicates(items: TListItems; index: Integer);
var i: Integer; isEqual: Boolean; begin items.BeginUpdate; for i := Pred(items.Count) downto 1 do begin if index < 0 then isEqual := AnsiSameText(items[Pred(i)].Caption, items[i].Caption) else isEqual := AnsiSameText(items[Pred(i)].Subitems[index], items[i].Subitems[index]); if isEqual then items[Pred(i)].Delete; end; items.EndUpdate; end; |
Re: TListView Duplikate rückwärts löschen
@marabu, dein Code funktioniert zwar, vergleicht aber nur die aufeinanderfolgenden Items auf Gleichheit und nicht alle, dazu sind 2 Schleifen nötig.
@frank, funktioniert solange bis die Prozedur versucht auf Items zuzugreifen die es soeben gelöscht hat, dann kommt ne EAccessViolation. Man müsste da noch prüfen ob das Item existiert und den Durchlauf überspringen. |
Re: TListView Duplikate rückwärts löschen
Hier ist noch eine Variante:
Delphi-Quellcode:
Gruß Hawkeye
procedure RemoveDuplicates (Items: TListItems; Index: Integer = -1);
var i : Integer; s : string; L : TStrings; begin L := TStringList.Create; for i := Items.Count - 1 downto 0 do begin if (Index < 0) then s := Items[i].Caption else s := Items[i].SubItems[Index]; if (L.IndexOf(s) < 0) then L.Add(s) else Items[i].Delete; end; L.Free; end; |
Re: TListView Duplikate rückwärts löschen
Zitat:
Gruß Frank |
Re: TListView Duplikate rückwärts löschen
Zitat:
marabu |
Alle Zeitangaben in WEZ +1. Es ist jetzt 16:06 Uhr. |
Powered by vBulletin® Copyright ©2000 - 2025, Jelsoft Enterprises Ltd.
LinkBacks Enabled by vBSEO © 2011, Crawlability, Inc.
Delphi-PRAXiS (c) 2002 - 2023 by Daniel R. Wolf, 2024 by Thomas Breitkreuz