Я работаю над программой, в C#, которая использует асинхронные сетевые вызовы. Некоторые из них изменяют коллекцию, из которой время от времени прокручивается остальная часть программы. Проблема заключается в том, что когда асинхронный вызов пытается изменить коллекцию во время цикла, генерируется исключение, и программа вылетает из строя.Стандартное решение для асинхронного вызова, мешающего сборке во время цикла?
Я довольно новичок в этом программировании, и это похоже на общую проблему, которая должна иметь стандартное решение.
Что я пытался было настроить bool, который я отключил, прежде чем перебирать коллекцию и проверить асинхронный метод. Если он не включен, я изменяю другую коллекцию и делаю изменения на основе этого оригинала в остальной части программы. Проблема заключается в том, что асинхронный метод также имеет цикл над этой коллекцией, поэтому, когда он вызывается последовательно, он может помешать этому циклу.
Я считаю, что лучшим решением было бы создать код, так что, если bool, означающий, что сбор не безопасен для изменения, прав, любой из этих вызовов задерживается. Однако я не знаю, является ли это достаточно хорошим решением (поскольку я полагаю, что асинхронный вызов может начаться сначала, тогда программа может попасть в небезопасную часть).
Это не фактическая программа, но пример задачи для ясности:
private List<Stuff> myList = new List();
private void NetworkDataReceived(Stuff s)
{
myList.Add(s);
}
private void SomeOtherMethod()
{
foreach(Stuff s in myList)
{
DoSomethingWithStuff(s);
}
}
В приведенном выше примере, когда NetworkDataReceived вызывается, когда SomeOtherMethod также работает, программа выходит из строя со следующим InvalidOperationException: " Коллекция была изменена, операция перечисления не может выполняться ».
Я был бы признателен, если бы кто-нибудь, у кого есть опыт программирования такого рода в C#, мог дать мне указатель на то, как решить эту проблему.
Посмотрите на [потокобезопасные коллекции] (https://msdn.microsoft.com/en-us/library/dd997305 (v = vs.110) .aspx) –
я изменил мой список в concurrentQueue и, похоже, решил проблему, большое спасибо! –