using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
namespace GSF.Net.Snmp.Security
{
///
/// Collection for improving performance. Using hashing of key/value pairs.
/// Oldest elements will be removed from the Cache when the capacity of the cache is reached.
/// This class is not thread safe.
///
/// The type of the keys in the dictionary.
/// The type of the values in the dictionary.
public class Cache
{
#region Data
private readonly Dictionary _dictionary;
private readonly Queue _keyQueue;
private readonly int _capacity;
#endregion //Data
#region Public_Properties
///
/// Gets the number of key/value pairs contained in the Cache.
///
public int Count
{
get
{
return _dictionary.Count;
}
}
#endregion //Public_Properties
#region Public_Methods
///
/// Caching class for improving performance. Oldest elements are removed as the
/// cache is filled up
///
/// Capacity of the cache before oldest elements start to get removed
public Cache(int initialCapacity)
{
_dictionary = new Dictionary(initialCapacity);
_keyQueue = new Queue(initialCapacity);
_capacity = initialCapacity;
}
///
/// Gets the value associated with the specified key.
///
/// The key of the value to get.
/// When this method returns, contains the value associated with the specified key,
/// if the key is found; otherwise, the default value for the type of the value parameter.
/// This parameter is passed uninitialized.
///
/// true if the Cache contains an element with the specified key; otherwise, false.
public bool TryGetValue(TKey key, out TValue value)
{
return _dictionary.TryGetValue(key, out value);
}
///
/// Determines whether the Cache contains the specified key.
///
/// The key to locate in the Cache
/// true if the Cache contains an element with the specified key; otherwise, false.
public bool ContainsKey(TKey key)
{
return _dictionary.ContainsKey(key);
}
///
/// Gets the value associated with the specified key.
///
/// The key of the value to get
/// key is null.
/// The property is retrieved and key does not exist in the collection.
/// The value associated with the specified key.
/// If the specified key is not found, a get operation throws a System.Collections.Generic.KeyNotFoundException,
/// and a set operation creates a new element with the specified key.
public TValue this[TKey key]
{
get { return _dictionary[key]; }
}
///
/// Adds the specified key and value to the dictionary. If the cache has reached
/// its capacity oldest element will be removed automatically
///
/// key is null
/// An element with the same key already exists in the Cache
/// The key of the element to add.
/// The value of the element to add.
public void Add(TKey key, TValue value)
{
if (IsCacheFull())
{
RemoveOldestElement();
}
_dictionary.Add(key, value); //Order of adding is important since dictionary can throw System.ArgumentNullException or System.ArgumentException
_keyQueue.Enqueue(key);
}
#endregion //Public_Methods
#region Private_Methods
///
/// Removes oldest element from the cache
///
private void RemoveOldestElement()
{
TKey keyToRemove = _keyQueue.Dequeue();
_dictionary.Remove(keyToRemove);
}
///
/// Checks whether cache size has reached the capacity
///
/// True if reached capacity false otherwise
private bool IsCacheFull()
{
return _keyQueue.Count() >= _capacity; //using >= instead of == in case someone doesn't syncronize Cache
}
#endregion //Private_Methods
}
}