c# – ConcurrentDictionary和ConcurrentQueue的这种组合是线程
发布时间:2020-12-15 08:18:56 所属栏目:百科 来源:网络整理
导读:我在以下代码中使用.NET 4中的ConcurrentDictionary和ConcurrentQueue类. 这段代码是线程安全的吗?如果没有,我怎样才能使它成为线程安全的? public class Page{ public string Name {get; set; }}public class PageQueue{ private ConcurrentDictionaryint
我在以下代码中使用.NET 4中的ConcurrentDictionary和ConcurrentQueue类.
这段代码是线程安全的吗?如果没有,我怎样才能使它成为线程安全的? public class Page { public string Name {get; set; } } public class PageQueue { private ConcurrentDictionary<int,ConcurrentQueue<Page>> pages = new ConcurrentDictionary<int,ConcurrentQueue<Page>>(); public void Add(int id,Page page) { if (!this.pages.ContainsKey(id)) this.pages[id] = new ConcurrentQueue<Page>(); this.pages[id].Enqueue(page); } public Page GetAndRemove(int id) { Page lp = null; if(this.pages.ContainsKey(id)) this.pages[id].TryDequeue(out lp); return lp; } } 演示: public class Demo { public void RunAll() { for (int i = 0; i < 10; i++) Task.Factory.StartNew(() => Run()); } public void Run() { PageQueue pq = new PageQueue(); pq.Add(1,new Page()); pq.GetAndRemove(1); } } 解决方法
正如@Femaref正确指出的那样,代码中存在一些缺陷.我建议你利用
ConcurrentDictionary<K,V>提供的许多方法使代码线程安全而不需要锁定语句:
public class PageQueue { private ConcurrentDictionary<int,ConcurrentQueue<Page>>(); public void Enqueue(int id,Page page) { var queue = this.pages.GetOrAdd(id,_ => new ConcurrentQueue<Page>()); queue.Enqueue(page); } public bool TryDequeue(int id,out Page page) { ConcurrentQueue<Page> queue; if (this.pages.TryGetValue(id,out queue)) { return queue.TryDequeue(out page); } page = null; return false; } } (编辑:李大同) 【声明】本站内容均来自网络,其相关言论仅代表作者个人观点,不代表本站立场。若无意侵犯到您的权利,请及时与联系站长删除相关内容! |