我已经使用了listView.BeginUpdate()
和listView.EndUpdate()
,但是当我删除25k中的100个项目时,它仍然需要10秒钟。
任何让它更快的想法和技巧?
编辑:
this.listView.BeginUpdate();
for (int i = this.listView.CheckedItems.Count - 1; i > -1; --i)
{
this.listView.CheckedItems[i].Remove();
}
this.listView.EndUpdate();
答案 0 :(得分:3)
您可以从这里开始优化:
List<int> toRemove = new List<int>();
foreach (ListViewItem item in this.listView.Items)
{
if (item.Checked) // check other remove conditions here
toRemove.Add(item.Index);
}
/* sort indices descending, so you'll remove items with higher indices first
and they will not be shifted when you remove items with lower indices */
toRemove.Sort((x, y) => y.CompareTo(x));
/* in this specific case you can simply use toRemove.Reverse();
or iterate thru toRemove in reverse order
because it is already sorted ascending.
But you might want to force sort it descending in some other cases.
*/
this.listView.BeginUpdate();
foreach (int itemIndex in toRemove)
this.listView.Items.RemoveAt(itemIndex); // use RemoveAt when possible. It's much faster with large collections
this.listView.EndUpdate();
答案 1 :(得分:0)
ListView将触发从列表中删除的每个项目的事件。您可以尝试通过清除整个ListView然后立即添加新的项目列表来避免这种情况,这些项目将被删除您要删除的100个项目。 这只会引发一些事件。
答案 2 :(得分:0)
那是因为每次从Items中删除元素时,ListView必须找到该项(walking the list to do so)并刷新CheckedItems集合(再次迭代所有剩余的项目),因此复杂性为O ^ 2。
最简单的方法是缓存SelectedIndices并使用listItem.Items.RemoveAt():
var selectedIndices = listView.SelectedIndices.Cast<int>().Reverse().ToList();
listView.BeginUpdate();
foreach (var index in selectedIndices) {
listView.Items.RemoveAt(index);
}
listView.EndUpdate();
如果您不想使用Cast&lt;&gt;扩展方法,你可以用第一行代替:
List<int> oToDelete = new List<int>(SelectedIndices.Count);
foreach (int iX in SelectedIndices)
{
oToDelete.Add(iX);
}
oToDelete.Reverse();