/// <summary> /// 保存数据 /// </summary> /// <param name="key"></param> /// <param name="value"></param> public void Set(TKey key, TValue value) { locker.EnterWriteLock(); try { dictionary[key] = value; LinkedListNode <TKey> item = null; if (dicLinkIndex.TryGetValue(key, out item)) { linkedList.Remove(item); } dicLinkIndex[key] = linkedList.AddFirst(key); if (linkedList.Count > _capacity) { dictionary.Remove(linkedList.Last.Value); dicLinkIndex.Remove(linkedList.Last.Value); linkedList.RemoveLast(); dicRefresh.Remove(linkedList.Last.Value); RemoveEntity <TKey, TValue> entity = new RemoveEntity <TKey, TValue>() { Key = linkedList.Last.Value, Value = dictionary[linkedList.Last.Value], RemoveType = RemoveType.Capacity }; removeEntities.Add(entity); dictionary.Remove(linkedList.Last.Value); } Refresh(key); } finally { locker.ExitWriteLock(); } }
/// <summary> /// 更新时间 /// </summary> /// <param name="key"></param> private void Refresh(TKey key) { dicRefresh[key] = DateTime.Now.Ticks; if (!isCheckTime) { return; } if (!isCheckThread) { isCheckThread = true; Task.Factory.StartNew(() => { double wait = (DateTime.Now - checkTime).TotalSeconds; if (wait < cacheTime) { //如果上次监测到本次监测还未到设置的保持时间, //则等待该时间差后再检查 double sleep = ((double)cacheTime - wait) * 1000 + 1; Thread.Sleep((int)sleep); } locker.EnterWriteLock(); try { LinkedListNode <TKey> last = null; long tick; long curTick = DateTime.Now.Ticks; last = linkedList.Last;//重后往前找 while (last != null) { if (dicRefresh.TryGetValue(last.Value, out tick)) { if ((curTick - tick) > checkTicks) { dicLinkIndex.Remove(last.Value); dicRefresh.Remove(last.Value); linkedList.RemoveLast(); RemoveEntity <TKey, TValue> entity = new RemoveEntity <TKey, TValue>() { Key = last.Value, Value = dictionary[last.Value], RemoveType = RemoveType.TimeOut }; removeEntities.Add(entity); dictionary.Remove(last.Value); } else { break; } } last = linkedList.Last; } } finally { locker.ExitWriteLock(); } isCheckThread = false; checkTime = DateTime.Now; }); } }
/// <summary> /// 启动移除通知 /// </summary> private void RemoveNotice() { Task.Factory.StartNew(() => { while (true) { RemoveEntity <TKey, TValue> item = null; if (removeEntities.TryTake(out item, 500)) { if (this.RemoveEntitiesEvent != null) { RemoveEntitiesEvent(CacheName, item); } } } }); }