Reputation: 3338
I have a dictionary which I would like to modify it's values in a foreach loop, however, since my application is time critical, I'm trying to avoid all unnecessary locking overheads.
var loopData = new Dictionary<int, List<string>>();
var results = new Dictionary<int, List<string>>();
/// loopData and results are both initialized
/// with same set of keys.
Parallel.ForEach(loopData, data =>
{
var list = data.Value;
/// manipulate list here
/// Is this safe?
results[data.Key] = list;
});
Is the marked command safe to do? i.e., read/write to different key-value pairs of a dictionary without locking.
Note 1: I'm aware of concurrent collections namespace and all it's magnificent collections. Also I know that I can simply lock
the highlighted command to ensure it's safety. As afore mentioned, my target is avoid unnecessary overheads as much as possible.
Note 2: a similar question is asked at this link. In that question the items of the container are modified inside the Parallel.ForEach
loop. Whereas, here we are not modifying the key-value pairs, therefore the container is intact, only the data being pointed is changed. This makes it different from aforementioned question.
Update
ConcurrentDictionary
would add least possible overhead, I would like to avoid it if this is safe.Upvotes: 2
Views: 6823
Reputation: 59641
From the comments I guess you have trouble understanding how many concurrent dictionaries you need. My annotations in code may help:
Parallel.ForEach(loopData, data =>
{
var list = data.Value; //<-- this is safe, because a read operation
/// manipulate list here <-- this is safe, because it operates on individual objects
/// Is this safe? <-- no, this is a write access
results[data.Key] = list;
});
So you need only one concurrent dictionary, and that is for the results
variable.
Upvotes: 1
Reputation: 127603
It is safe to read from the dictionary concurrently but it is not safe to write to it concurrently or read from it while writing concurrently. ConcurrentDictionary
will be your fastest option for concurrent inserts.
Upvotes: 11