C# 我应该使用什么作为System.Collections.Concurrent.ConcurrentDictionary(3.5)的替代方案
我需要线程安全集合,但无法将ConcurrentDictionary用作.NET4.0,我需要使用.NET3.5。有哪些替代方案?看看这篇文章C# 我应该使用什么作为System.Collections.Concurrent.ConcurrentDictionary(3.5)的替代方案,c#,.net-3.5,C#,.net 3.5,我需要线程安全集合,但无法将ConcurrentDictionary用作.NET4.0,我需要使用.NET3.5。有哪些替代方案?看看这篇文章 您可以创建一个简单的包装器,只实现您需要的功能。请记住,在依赖于上一次调用结果的字典上执行操作不是线程安全的。这在TryAdd方法中得到了示例 class ConcurrentMap<K, V> { readonly Dictionary<K, V> _map = new Dictionary<K, V>();
您可以创建一个简单的包装器,只实现您需要的功能。请记住,在依赖于上一次调用结果的字典上执行操作不是线程安全的。这在
TryAdd
方法中得到了示例
class ConcurrentMap<K, V>
{
readonly Dictionary<K, V> _map = new Dictionary<K, V>();
public bool TryGetValue(K key, out V value)
{
lock (_map)
{
return _map.TryGetValue(key, out value);
}
}
public bool TryAdd(K key, V value)
{
lock (_map)
{
if (!_map.ContainsKey(key))
{
_map.Add(key, value);
return true;
}
return false;
}
}
public bool TryRemove(K key)
{
lock (_map)
{
return _map.Remove(key);
}
}
}
类ConcurrentMap
{
只读字典_map=新字典();
公共布尔TryGetValue(K键,输出V值)
{
锁(_映射)
{
返回_map.TryGetValue(键,输出值);
}
}
公共bool TryAdd(K键,V值)
{
锁(_映射)
{
如果(!\u地图容器(键))
{
_添加(键、值);
返回true;
}
返回false;
}
}
公共bool TryRemove(K键)
{
锁(_映射)
{
返回_map.Remove(键);
}
}
}
最后我找到了我想要的东西。第三方物流的nuget包后端口为3.5。可以在这里找到
对于框架3.5,我可以看到以下选项:
- 字典+。简单的包裹锁定
- 字典+。比前一个更好,因为它有读写锁。因此,多个线程可以读取,而只有一个线程可以写入
- 字典+。这只是对前一个的优化
- 。根据我的经验,这是最慢的方法。检查方法,这是Microsoft提供的现成解决方案
我会使用Dictionary+ReaderWriterLock或readerwriterlocksim。我只需要.NET3.5中使用它。。。后面还有人:) 添加我的类,添加了比以前附加的代码更多的功能
public class SafeDictionary<TKey, TValue> : IEnumerable<KeyValuePair<TKey, TValue>>
{
private readonly object _Padlock = new object();
private readonly Dictionary<TKey, TValue> _Dictionary = new Dictionary<TKey, TValue>();
public TValue this[TKey key]
{
get
{
lock (_Padlock)
{
return _Dictionary[key];
}
}
set
{
lock (_Padlock)
{
_Dictionary[key] = value;
}
}
}
public bool TryGetValue(TKey key, out TValue value)
{
lock (_Padlock)
return _Dictionary.TryGetValue(key, out value);
}
public bool TryAdd(TKey key, TValue value)
{
lock (_Padlock)
{
if (!_Dictionary.ContainsKey(key))
{
_Dictionary.Add(key, value);
return true;
}
return false;
}
}
public bool TryRemove(TKey key)
{
lock (_Padlock)
{
return _dictionary.Remove(key);
}
}
}
internal void Add(TKey key, TValue val)
{
lock (_Padlock)
{
_Dictionary.Add(key, val);
}
}
public bool ContainsKey(TKey id)
{
lock (_Padlock)
return _Dictionary.ContainsKey(id);
}
public List<KeyValuePair<TKey, TValue>> OrderBy(Func<KeyValuePair<TKey, TValue>, TKey> func)
{
lock (_Padlock)
return _Dictionary.OrderBy(func).ToList();
}
public Dictionary<TKey, TValue>.ValueCollection Values
{
get
{
lock (_Padlock)
return _Dictionary.Values;
}
}
public Dictionary<TKey, TValue>.KeyCollection Keys
{
get
{
lock (_Padlock)
return _Dictionary.Keys;
}
}
IEnumerator<KeyValuePair<TKey, TValue>> IEnumerable<KeyValuePair<TKey, TValue>>.GetEnumerator()
{
lock (_Padlock)
return _Dictionary.GetEnumerator();
}
IEnumerator IEnumerable.GetEnumerator()
{
lock (_Padlock)
return _Dictionary.GetEnumerator();
}
}
公共类安全字典:IEnumerable
{
私有只读对象_挂锁=新对象();
专用只读词典_Dictionary=新词典();
公共TValue此[TKey]
{
得到
{
锁(挂锁)
{
返回字典[键];
}
}
设置
{
锁(挂锁)
{
_字典[键]=值;
}
}
}
公共bool TryGetValue(TKey键,out TValue值)
{
锁(挂锁)
返回_Dictionary.TryGetValue(键,输出值);
}
公共bool TryAdd(TKey键,TValue值)
{
锁(挂锁)
{
if(!\u字典.ContainsKey(键))
{
_添加(键、值);
返回true;
}
返回false;
}
}
公共bool TryRemove(TKey)
{
锁(挂锁)
{
返回_dictionary.Remove(键);
}
}
}
内部无效添加(TKey key,TValue val)
{
锁(挂锁)
{
_Dictionary.Add(key,val);
}
}
公共bool ContainsKey(TKey id)
{
锁(挂锁)
返回_Dictionary.ContainsKey(id);
}
公共列表排序依据(Func Func)
{
锁(挂锁)
return _Dictionary.OrderBy(func.ToList();
}
public Dictionary.ValueCollection值
{
得到
{
锁(挂锁)
返回_Dictionary.Values;
}
}
public Dictionary.KeyCollection密钥
{
得到
{
锁(挂锁)
返回_Dictionary.Keys;
}
}
IEnumerator IEnumerable.GetEnumerator()
{
锁(挂锁)
返回_Dictionary.GetEnumerator();
}
IEnumerator IEnumerable.GetEnumerator()
{
锁(挂锁)
返回_Dictionary.GetEnumerator();
}
}
您将使用哪个版本?以3.5为目标,ConcurrentDictionary is 4.0(抱歉,标题有误导性)总是可以退回到使用锁的类中包装标准字典。+1作为文章的链接,因为(通常)它不仅仅是在常规字典的所有操作上加锁。不过,您可能想在答案中“提取”一些关键点。