Determining whether an object implements the generic version of IDictionary isn't as easy as it seems. Ideally this would work:
Unfortunately, it doesn't. Leaving out type parameters (i.e. "<,>") is supported only with the typeof operator.
So, after some experimentation, here's how you can do that type of test, and then invoke a generic method with type parameters:
class Program
{
private static readonly MethodInfo _doStuffMethod = typeof(Program).GetMethod("DoStuff");
static void Main()
{
Dictionary<string, int> map = new Dictionary<string, int>();
Encode(map);
}
static void Encode(object val)
{
if (val is IEnumerable)
{
Type valType = val.GetType();
if (valType.IsGenericType)
{
foreach (Type valInterface in valType.GetInterfaces())
{
if (valInterface.IsGenericType && typeof(IDictionary<,>).IsAssignableFrom(valInterface.GetGenericTypeDefinition()))
{
Type[] valTypeParams = valInterface.GetGenericArguments();
_doStuffMethod.MakeGenericMethod(valTypeParams[0], valTypeParams[1]).Invoke(null, new object[] { val });
}
}
}
}
}
public static void DoStuff<K, V>(IDictionary<K, V> dic)
{
Console.WriteLine(dic.ToString());
}
}