关于ConcurrentQueue--一个队列缓存的设计
using System; using System.Collections.Generic; using System.Linq; using System.Web; using System.Collections.Concurrent; namespace PDAJob.PDAService.Service { public class CacheList<T> { private int MaxSize = 10000; private int ShrinkLen = 2000; private ConcurrentQueue<CacheItem<T>> _Queue = new ConcurrentQueue<CacheItem<T>>(); public CacheList(int maxSize,int shrinkLen) { this.MaxSize = maxSize; this.ShrinkLen = shrinkLen; } public void Add(T item) { #region 超过则收缩 if (_Queue.Count >= MaxSize) { lock (this) { if (_Queue.Count >= MaxSize) { CacheItem<T> outItem; for (int i = 0; i < ShrinkLen; i++) { _Queue.TryDequeue(out outItem); } } } } #endregion _Queue.Enqueue(new CacheItem<T>() { Data = item, AddTime = DateTime.Now }); } public ConcurrentQueue<CacheItem<T>> Queue { get { return _Queue; } } } /// <summary> /// 缓存内容 /// </summary> /// <typeparam name="T"></typeparam> public class CacheItem<T> { public DateTime AddTime { get; set; } public T Data { get; set; } } }
在多线程环境下可能多个Thread读到Queue.Count>MaxSize,虽然Queue是Thread安全的,但是上面的代码可造成_Queue被重复移空,所以要加lock