Dictionary<T> look-up or create made simpler

The design of a Dictionary<T> lends itself well to a caching or identification mechanism and as a result you often see code that looks like this:

private static Dictionary<string, Employee> employees = new Dictionary<string, Employee>();

public static Employee GetByName(string name) {
  Employee employee;
  if (!employees.TryGetValue(name, out employee)) {
    employee = new Employee(whatever);
    employees.Add(name, employee);
  }
  return employee;
}

It’s not that it is particularly difficult but it can be a bit error prone and when you’re doing it over and over. What would be nicer is something that let you do:

public static Employee GetByName(string name) {
  return employees.GetOrAdd(name, () => new Employee(whatever));
}

Here’s an extension method to drop-in to a static class of your choosing that achieves just that.

public static TDictionaryValue GetOrAdd<TKey, TDictionaryValue>(
  this IDictionary<TKey, TDictionaryValue> dictionary,
  TKey key,
  Func<TDictionaryValue> newValue
) {
  TDictionaryValue value;
  if (!dictionary.TryGetValue(key, out value)) {
    value = newValue.Invoke();
    dictionary.Add(key, value);
  }
  return value;
}

[)amien

6 responses to Dictionary<T> look-up or create made simpler

  1. Avatar for

    Information is only used to show your comment. See my Privacy Policy.

  2. Avatar for Mike Brown
    Mike Brown

    Interesting that this became a function on the ConcurrentDictionary class in .NET 4 ;)

  3. Avatar for Brad Wilson

    Using double checked locking without knowing that the variable in question is marked “volatile” is a potential source of threading errors.

  4. Avatar for Will

    Nice one

    Definitely I have to get used to the use of extension methods, it seems really obvious after you’ve seen it, but if you haven’t used extension methods it is hard for it to “pop up”

    Cheers!

  5. Avatar for Damien Guard

    Oops, the code was right on my VS box but going from code to HTML I’d missed a couple of those pesky < bits :D

    Thanks for the heads-up.

  6. Avatar for Nick

    Heya Damien, did you mean to use the non-generic IDictionary interface in your static method signatures?