I have a bit of code that works like this on a list of obj objects called ListofObjects:
List<SomeObject> NewListofObjects<SomeObject>();
Parallel.ForEach(ListofObjects, obj =>
//Do some operations here on obj to get a newobj
NewListofObjects.Add(newobj);
);
Now I am out of the Parallel.ForEach loop, and I want to do an operation on NewListofObjects. However, I get this error when I try to: "Attempted to read or write protected memory. This is often an indication that other memory is corrupt".
Is this because my NewListofObjects.Add(newobj) method is not threadsafe? If so, how can I make it threadsafe?
Is this because my
NewListofObjects.Add(newobj)
method is not threadsafe?
Correct. It is not threadsafe.
Any instance members are not guaranteed to be thread safe.
That's from MSDN referring to List<T>
(scroll to the section titled "Thread Safety").
If so, how can I make it threadsafe?
Use a concurrent collection, like ConcurrentBag<T>
. Note that you lose the ability to keep track of the order that items were inserted.
You can use the locking
block like the following code to insert items into your list in a thread-safe manner.
var sync = new object();
var myNewList = new List<SomeObject>();
Parallel.ForEach(myListOfSomethings, a =>
{
// Some other code...
var someObj = new SomeObject();
// More other code...
lock(sync)
{
myNewList.Add(someObj);
}
// Even more code...
});
The .NET Framework 4 introduces the System.Collections.Concurrent namespace, which includes several collection classes that are both thread-safe and scalable. https://learn.microsoft.com/en-us/dotnet/standard/collections/thread-safe/
BlockingCollection<int>[] sourceArrays = new BlockingCollection<int>[5];
for (int i = 0; i < sourceArrays.Length; i++)
sourceArrays[i] = new BlockingCollection<int>(500);
Parallel.For(0, sourceArrays.Length * 500, (j) =>
{
int k = BlockingCollection<int>.TryAddToAny(sourceArrays, j);
if (k >= 0)
Console.WriteLine("added {0} to source data", j);
});
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With