I have a Canvas
with a lot of little Canvas inside. If I click any of them, it creates a Thread
with a specific method (add another little canvas to the main canvas and move around it for example). I need to make some of those little canvas grow when I click a specific button. So I tried with a foreach
loop but the application crashes and shows me this error:
InvalidOperationException: Collection was modified; enumeration operation may not execute
I thought that happens because there was a context switching, so I added a lock to the method, but the problem continues. My code is below:
private void BacteriaPsiEspecial(object sender , MouseButtonEventArgs e)
{
lock (sender)//Maybe here is the problem
{
//The application crashes here
foreach (Canvas LittleCanvas in CanvasSimulador.Children)
{
if(LittleCanvas.Uid.Equals("SomeId"))
{
//Method to make each one grow growMethod()
}
}
}
}
I don't know if foreach
works to do this. I have to use a lot of threads because all the little canvases are continually moving around the main canvas. The question is, what can I do to make some of those canvas be affected by growMethod()?
It sounds like you have multiple threads changes the collection you're trying to foreach
over. Simply put, this won't work. Here are a few options I can think of:
growMethod()
takes a significant amount of time, you could try getting a copy of the list before iterating over it... the LINQ extension methods .ToList()
or .ToArray()
should work. But you'd probably still hit the exception, so you might end up adding retry logic, etc... yuck. You could potentially limit access to your collection by putting a lock around when you access and modify it:
private IEnumerable<Canvas> GetLittleChildren() { lock(lockObject) { return CanvasSimulador.Children.ToArray(); } } private IEnumerable<Canvas> AddChild(Canvas littleCanvas) { lock(lockObject) { CanvasSimulador.Children.Add(littleCanvas); } } private IEnumerable<Canvas> RemoveChild(Canvas littleCanvas) { lock(lockObject) { CanvasSimulador.Children.Remove(littleCanvas); } }
I'm still not convinced that's a good method, but it might work...
The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.