ConcurrentDictionary
is the thread safe counterpart to the generic dictionary
collection. Both are designed for quick lookups of data based on a key. However, ConcurrentDictionary
allows us to interleave both reads and updates. ConcurrentDictionary
achieves its thread safety with no common lock to improve efficiency. It actually uses a series of locks to provide concurrent updates, and has lockless reads.
In this recipe, we will create
ConcurrentDictionary
and initialize it with a small set of key value pairs. Our dictionary
will be concurrently updated by one task and read by another.
Let's take a look at how to use ConcurrentDictionary
for data lookups.
ConcurrentDictionary
as the Solution name.using
directives to the top of your Program
class:using System; using System.Collections.Concurrent; using System.Collections.Generic; using System.Linq; using System.Text; using System.Threading.Tasks;
ConcurrentDictionary
and initialize it with some data.var dictionary = new ConcurrentDictionary<string, int>(); dictionary["A"] = 1; dictionary["B"] = 2; dictionary["C"] = 3; dictionary["D"] = 4; dictionary["E"] = 5; dictionary["F"] = 6; dictionary["G"] = 7; dictionary["H"] = 8; dictionary["I"] = 9; dictionary["J"] = 10; dictionary["K"] = 11; dictionary["L"] = 12; dictionary["M"] = 13; dictionary["N"] = 14; dictionary["O"] = 15;
Task
to update dictionary
on a separate thread.// update dictionary on a separate thread Task.Factory.StartNew(() => { foreach (var pair in dictionary) { var newValue = pair.Value + 1; dictionary.TryUpdate(pair.Key,newValue,pair.Value); Console.WriteLine("Updated key: {0} value:{1}", pair.Key, newValue); } });
Task
which will be concurrently reading from dictionary
.Task.Factory.StartNew(() => { foreach (var pair in dictionary) { Console.WriteLine("Reading key: {0} value:{1}",pair.Key,pair.Value); } }); Console.ReadLine();
ConcurrentDictionary
behaves like dictionary
counterpart with slight differences. We are updating dictionary
using the TryUpdate
method. This method was added to provide us with an atomic operation to check if the item exists, and if not, add it while still under an atomic lock.
foreach (var pair in dictionary) { var newValue = pair.Value + 1; dictionary.TryUpdate(pair.Key,newValue,pair.Value); Console.WriteLine("Updated key: {0} value:{1}", pair.Key, newValue); }
We are reading dictionary
directly from the Key
and Value
properties of each KeyValuePair
in the collection.
3.17.203.68