ConcurrentDictionary and Clear () are a function. Creating stream export values ​​without data loss

Any ideas on creating a ConcurrentDictionary threadsafe in a state in which values ​​are exported to an ex list, and after that the dictionary is cleared. So any other stream cannot add data between export and cleanup.

Like this: "

List<data> list; list = (List<data>)_changedItems.Values; //get values before clearing _changedItems.Clear(); 

"And adding is done by other threads with _changedItems.AddOrUpdate function

Now it is possible to lose new data between receiving data from the dictionary and clearing the contents if some stream adds data objects to the collection before the clearing line.

Or is this the only way to do add and clear inside the lock.

 lock(object) { List<data> list; list = (List<data>)_changedItems.Values; _changedItems.Clear(); } 

AND

 lock(object) _changedItems.AddOrUpdate 

There is a need for a Clear function that safely returns all cleared items from a dictionary.

-Larry

+4
source share
2 answers

Indeed, calling two thread-safe methods in a sequence does not guarantee the atomicity of the sequence itself. You are correct that you need a lock on both calls to get values ​​and clear.

+2
source

You can use the TryRemove(key, out value) method. It returns the deleted item. This way, you do not need to lock the dictionary to move buffered data.

 List<data> list; var keys = dict.Keys; foreach(var key in keys) { data value; dict.TryRemove(key, out value); list.Add(value); } 

Update: in fact, you can iterate directly over the ConcurrentDictionary , even if it changes. This way you do not need to create a key collection from the .Keys property, which can be (?) Slow, depending on the implementation.

 List<data> list; foreach(var kvp in dict) { data value; dict.TryRemove(kvp.Key, out value); list.Add(value); } 
0
source

Source: https://habr.com/ru/post/1392682/


All Articles