Très souvent, je besoin de quelque chose comme ça:Meilleure pratique pour éviter InvalidOperationException: la collection a été modifiée?
foreach (Line line in lines)
{
if (line.FullfilsCertainConditions())
{
lines.Remove(line)
}
}
Cela ne fonctionne pas, parce que je reçois toujours un InvalidOperationException
parce que le recenseur a été changé au cours de la boucle.
Je changé toutes mes boucles de ce genre à ce qui suit:
List<Line> remove = new List<Line>();
foreach (Line line in lines)
{
if (line.FullfilsCertainConditions())
{
remove.Add(line)
}
}
foreach (Line line in remove) {
{
lines.Remove(line);
}
Je ne sais pas si cela est vraiment la meilleure façon puisque dans le pire des cas, je dois itérer 2 fois l'original liste et donc il a besoin de temps 2n au lieu de n.
Y a-t-il une meilleure façon de procéder?
EDIT:
j'ai pu le faire en utilisant la réponse de Mark Mais si ma collection ne met en œuvre RemoveAll()?
Par exemple, un
System.Windows.Controls.UIElementCollection
EDIT 2:
Encore une fois, avec l'aide de Mark, je suis maintenant en mesure de faire l'appel suivant à supprimer tout ScatterViewItems:
CollectionUtils.RemoveAll(manager.getWindow().IconDisplay.Items, elem => elem.GetType() == typeof(ScatterViewItem));
J'ai eu le même problème il y a quelque temps et pas de solution. C'est encore pire - ce n'est pas 2n mais n^2 puisque 'lines.Remove (line)' se répète sur la collection. – Matten
Mais O (2n) est égal à O (n) :-) vraiment: En Java, vous pouvez utiliser un Iterator pour ce faire, ou opter pour une implémentation de Copy-on-Write Collection qui permet des modifications pendant l'itération. – Waldheinz
Re la mise à jour - voir mon edit –