0

I'm trying to pass an expression that describes a method but I want the argument to be strongly typed and I don't want to have to know the method signature or pass the arguments in the expression, something like this:

GetMethod<MyClass>(c => c.DoSomething); 

Where DoSomething could have a method signature like this... string DoSomething(int id, int count)

I know I can do something like this:

MemberInfo GetMethod<T>(Expression<Func<T, Delegate>> expression); //implementation GetMethod<MyClass>(c => new Func<int, int, string>(c.DoSomething)) 

But frankly, this is quite ugly.

Is this possible?

1 Answer 1

5

Just have an overload for each possible Action/Func. It won't cover all possibilities (have an extra overload that you've shown there to cover all edge cases) but it'll handle most of them.

The body of each of the action/func overloads can just call the overload that you've shown above for the actual implementation.

public MemberInfo GetMethod<T1, T2>(Expression<Func<T1, Func<T2>>> expression) { return GetMethodImpl(expression); } public MemberInfo GetMethod<T1, T2, T3>(Expression<Func<T1, Func<T2, T3>>> expression) { return GetMethodImpl(expression); } public MemberInfo GetMethod<T1, T2>(Expression<Func<T1, Action<T2>>> expression) { return GetMethodImpl(expression); } //... 

GetMethodImpl can then be implemented like so:

private MemberInfo GetMethodImpl<T1, T2>(Expression<Func<T1, T2>> expression) { } 

That will be able to be just a slight modification of your existing GetMethod implementation. T2 will be your delegate; you may need to cast it to Delegate, depending on how you use it.

Sign up to request clarification or add additional context in comments.

11 Comments

I'm looking for something more scalable. There could potentially be tens, if not hundreds, of different method signatures.
@bflemi3 There are only 16? different overloads to Func and Action, each. That's a finite list. Generics help handle the permutations that scale it up to a huge level. As long as you don't have a lot of methods with more than 16 arguments it's not a huge issue. It won't handle any methods with ref/out arguments, optional arguments, params arguments, or possibly a few other edge cases. For those you'll need to use the method you showed in the OP as it's probably just not worth dealing with special overloads just for them.
Would you mind giving me a quick implementation example? I guess using string DoSomething(int id, int count)
@bflemi3 The implementation is whatever you had to begin with. The idea is that this ensures compile time safety in behalf of the caller, but then turns the strongly typed delegate into just a Delegate and does whatever you were doing before. I have no idea what that is.
I'm confused then, which signature above would match my implementation?
|

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.