I have a class that contains a Dictionary field. I would like to log each insert to the dictionary. What is the most elegant way to do that?
I tried to define a property of the dictionary, and to put the log in the set
method:
private Dictionary<string, string> _myDictionary = new Dictionary<string, string>();
private Dictionary<string, string> MyDictionary
{
get
{
return _myDictionary;
}
set
{
_logger.Trace($"MyDictionary.set: value = {value}");
_myDictionary = value;
}
}
but it is not relevant for an insert, only for an assignment for the dictionary reference. I would like to "catch" the set of a key-value like in the following operation, and log it:
MyDictionary["key"] = "some value";
How?
CodePudding user response:
You could create a class that derives from Dictionary<TKey, TValue>
and replace the standard Add method and the indexer property adding some kind of logging before calling the base implementation
public class LoggedDictionary<TKey, TValue> : Dictionary<TKey, TValue>
{
public new void Add(TKey key, TValue value)
{
// Replace with whatever logging method you use
Console.WriteLine($"Add called {key} = {value}");
base.Add(key,value);
}
public new TValue this[TKey key]
{
get
{
// Replace with whatever logging method you use
Console.WriteLine("Get called");
return base[key];
}
set
{
// Replace with whatever logging method you use
Console.WriteLine($"Set called {key} = {value}");
base[key] = value;
}
}
}
void Main()
{
LoggedDictionary<string, string> logged = new LoggedDictionary<string, string>();
logged.Add("test", "t1");
logged["test"] = "t2";
}
If your intent is to log every action that changes the dictionary then you need to redefine also the Remove methods
public new bool Remove(TKey key)
{
Console.WriteLine($"Remove called for {key}");
return base.Remove(key);
}
public new bool Remove(TKey key, out TValue value)
{
Console.WriteLine($"Remove called for {key}");
return base.Remove(key, out value);
}