Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Lambda expression that returns a delegate

Hi I am trying to achive something like this;

Method<TObjectType>(m=>m.GetData); //m is the instance of TObjectType

if I can succeed on that, then I can visit this expression and get the GetData Method and use it for creating a dynamic sql query. I could do this by giving method name as a string however I don't want to break the strongly type world of my developer friends.

I know I have to give the exact definition of the delegate but this still doesn't helped me;

void Method<TObjectType>(Expression<Func<TObjectType, Delegate>> ex){/**/}

Do you have an idea?

like image 624
Mert Susur Avatar asked Jul 31 '12 07:07

Mert Susur


1 Answers

Unfortunately, there's barely such a thing as "a delegate". For most purposes (and especially: for resolving a MethodInfo), it must be a strongly-typed delegate. This is because GetData isn't a method, it is a method group. You really need to specify the method precisely, or have a known delegate-type (which ultimately does the same thing).

You have two practical options; work to object, or add a generic. For example:

void Method<TObjectType>(Expression<Func<TObjectType,object>> ex) {...}

would work, as would:

void Method<TObjectType, TValue>(Expression<Func<TObjectType,TValue>> ex) {...}

The caller would use:

Method<Foo>(x => x.GetData());

If you really want to use a delegate, the type must be predictable, for example:

void Method<TObjectType>(Expression<Func<TObjectType,Func<int>>> ex)

allowing:

Method<Foo>(x => x.GetData);

Alternatively, if you know (for example) that the method is always parameterless, but you don't know the return type; maybe something like:

void Method<TObjectType, TValue>(Expression<Func<TObjectType,Func<TValue>>> ex)

which allows:

Method<Foo, int>(x => x.GetData);
like image 134
Marc Gravell Avatar answered Sep 21 '22 09:09

Marc Gravell