Suppose I have a method with many overloads, such as Console.WriteLine
, which I want to fetch via Reflection. I have a dynamic
value x
and want to fetch the most relevant method for x
's type, like this:
var consoleType = Type.GetType("System.Console")
dynamic x = "Foo";
GetMethodFromParams(consoleType, "WriteLine", new[] {x}); // => [Void WriteLine(string)]
x = 3;
GetMethodFromParams(consoleType, "WriteLine", new[] {x}); // => [Void WriteLine(int)]
x = new SomeClass();
GetMethodFromParams(consoleType, "WriteLine", new[] {x}); // => [Void WriteLine(object)]
From what I can see, you can only fetch a method if you know the parameter types of the method, otherwise an exception is thrown:
> Type.GetType("System.Console").GetMethod("WriteLine")
Ambiguous match found.
+ System.RuntimeType.GetMethodImpl(string, System.Reflection.BindingFlags, System.Reflection.Binder, System.Reflection.CallingConventions, System.Type[], System.Reflection.ParameterModifier[])
+ System.Type.GetMethod(string)
> Type.GetType("System.Console").GetMethod("WriteLine", new[] { Type.GetType("System.String") })
[Void WriteLine(System.String)]
How could I implement the GetMethodFromParams
method demonstrated above? One idea I had was using the Type.GetType(...).GetMethods()
method and filtering through the results based on their parameter types compared to x
's type, but this might be tricky to get working with covariance and contravariance.
Turns out, you can simply use x.GetType()
to get x
's type and pass that as an array element to GetMethod
and it works great, even for covariance and contravariance. This means you could implement this like so:
public static MethodInfo GetMethodFromParams(Type t, string methodName, dynamic[] args)
=> t.GetMethod(methodName,
args.Select(x => (Type)x.GetType())
.ToArray());