最近在做项目时,多线程中使用Dictionary
的全局变量时,发现数据并没有存入到Dictionary
中,但是程序也没有报错,经过自己的一番排查,发现Dictionary为非线程安全类型,因此我感觉数据没有写进去的原因是多线程在争夺全局变量时,导致数据未写入,于是去对Dictionary
进行仔细的了解。
经过在网上查阅资料,发现大家讲解最多的是Dictionary
(非线程安全)和ConcurrentDictionary
(线程安全),于是我也从这两个关键字来仔细的讲解,顺便也更加深入的认识它们。
Dictionary
怎样解决线程安全问题?可以使用加锁、线程全局变量、使用ConcurrentDictionary
等。下面我们就一起来看看吧,Let’s go。
Dictionary
Dictionary<TKey, TValue>
泛型类提供了键值对映射,通过TKey
来检索值的速度非常快,时间复杂度接近与O(1),是因为Dictionary
通过哈希表实现,是一种变相的HashTable
,采用分离链接散列表的数据结构解决哈希冲突问题。
在早期的C#版本中,可以将集合初始值设定项用于序列样式集合,包括在键值对周围添加括号而得到Dictionary<TKey, TValue>
,如:
Dictionary<int, string> msgs = new Dictionary<int, string>()
{
{
1, "Hello, "},
{
2 , "World"},
{
3, "!"}
};
而新的语法支持使用索引分配到集合中,如:
Dictionary<int, string> MsgErrs = new Dictionary<int, string>()
{
[1] = "Hello, ",
[2] = "World",
[3] = "!",
};
上述两者在初始化赋值时都差不多,但是两者还是有一些区别,前者在初始化时出现重复key
值,程序会直接报错。而后者初始化时,key
可以有重复值,系统会自动过滤掉重复的key
值,程序也不会报错。
实现键/值对集合
每次对字典的添加都包含一个值与其关联的值,通过使用键来检索十分方便;
如果使用集合初始值设定项生成Dictionary
集合,可以使用如下方法:
public static Dictionary<string, Element> BuildDic()
{
return new Dictionary<string, Element>
{
{
"L", new Element(){
Symbol = "L", Name = "Postass", AutominNumber = 9}},
{
"Q", new Element(){
Symbol = "Q", Name = "Calcium