Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Calling generic method using reflection in .NET [duplicate]

I have a question. Is it possible to call generic method using reflection in .NET? I tried the following code

var service = new ServiceClass(); Type serviceType = service.GetType(); MethodInfo method = serviceType.GetMethod("Method1", new Type[]{}); method.MakeGenericMethod(typeof(SomeClass)); var result = method.Invoke(service, null); 

But it throws the following exception "Late bound operations cannot be performed on types or methods for which ContainsGenericParameters is true."

like image 357
yshchohaleu Avatar asked Jun 01 '11 16:06

yshchohaleu


People also ask

Can we invoke generic method using .NET reflection?

Calling a generic method with a type parameter known only at runtime can be greatly simplified by using a dynamic type instead of the reflection API. To use this technique the type must be known from the actual object (not just an instance of the Type class).

Do generics use reflection?

Because the Common Language Runtime (CLR) has access to generic type information at run time, you can use reflection to obtain information about generic types in the same way as for non-generic types.

How do you call a generic function in C#?

MethodInfo method = typeof(Foo). GetMethod("MyGenericMethod"); method = method. MakeGenericMethod(t); method. Invoke(this, new object[0]);


2 Answers

You need to say

method = method.MakeGenericMethod(typeof(SomeClass)); 

at a minumum and preferably

var constructedMethod = method.MakeGenericMethod(typeof(SomeClass)); constructedMethod.Invoke(service, null); 

as instances of MethodInfo are immutable.

This is the same concept as

string s = "Foo "; s.Trim(); Console.WriteLine(s.Length); string t = s.Trim(); Console.WriteLine(t.Length); 

causing

4 3 

to print on the console.

By the way, your error message

"Late bound operations cannot be performed on types or methods for which ContainsGenericParameters is true."

if your clue that method still contains generic parameters.

like image 22
jason Avatar answered Nov 22 '22 15:11

jason


You're not using the result of MakeGenericMethod - which doesn't change the method you call it on; it returns another object representing the constructed method. You should have something like:

method = method.MakeGenericMethod(typeof(SomeClass)); var result = method.Invoke(service, null); 

(or use a different variable, of course).

like image 148
Jon Skeet Avatar answered Nov 22 '22 16:11

Jon Skeet