0

Related To: Create a Lambda Expression With 3 conditions

Please consider this GroupBy statement:

group r by new { r.EmployeeID, r.Name }

If I want to write above GroupBy statement with Lambda version and pass Expression<Func<T, TKey>> to it as parameter, How I can create Expression<Func<T, TKey>>?

Arian
  • 12,793
  • 66
  • 176
  • 300
  • 1
    @shA.t: No, by "dynamically" I'm pretty sure he means he doesn't want to have the code specify EmployeeID and Name at compile-time. He wants to use information known at run-time instead. – StriplingWarrior Sep 19 '17 at 05:13
  • Thanks but I want to create `Expression> using `Expressions`. Please see the link that refered to – Arian Sep 19 '17 at 05:13
  • @StriplingWarrior Yes You are right – Arian Sep 19 '17 at 05:14
  • 1
    What information do you have at the time you construct this expression? Do you know which values make up the group key? Do you know their types? Can you include some code showing a sample use case? – Mike Strobel Sep 19 '17 at 13:15

1 Answers1

3

I don't have time to walk you through the whole thing, but the general gist is that you'll construct expressions using static methods off of the Expression class.

For example, the new expression will be created by passing constructor information and a series of expressions and such to one of the Expression.New() overloads.

The concept of r => ... is embodied by Expression.Lambda<Func<T, TKey>>(...) where you pass an Expression.Parameter(typeof(T), "r") as the lambda's parameter.

Expression.MakeMemberAccess will help you to produce r.EmployeeId and r.Name.

I find it useful to start by dumping a sample expression in LINQPad with code like this:

void Main()
{
    DumpExp(r => new { r.EmployeeID, r.Name });
}

public void DumpExp<TKey>(Expression<Func<Foo, TKey>> expr)
{
    expr.Dump();
}

public class Foo
{
    public string EmployeeID;
    public string Name;
}

That will allow you to inspect the tree and understand what types of expressions make up the tree, and what the values of their properties are. Then you can try writing code to match.

Once you've got an Expression that you think will work, you can call Compile on it to produce a runnable function, which you can use to test its behavior on in-memory objects.

I'm guessing the anonymous type you've got there may be the most difficult part of the problem. If the target framework supports something like Tuples in its GroupBy statements, you will probably be better off using those instead.

There is an oldish project that was designed to enable you to run dynamic LINQ statements built by providing strings to LINQ-like methods. It's called "Dynamic LINQ", and it might suit your needs.

You might also find this library useful. It's supposed to help you build Expression trees with a more fluent syntax. However, it doesn't appear to be under active development.

StriplingWarrior
  • 151,543
  • 27
  • 246
  • 315
  • Great answer...There is a few Documentation on this topic and if it is possible for you, i wanted to ask you write above statement here. I didn't use expressions this way and if I can see a working sample It will very helpful to search properly – Arian Sep 19 '17 at 05:56
  • @Arian: I don't have time to write this for you, but you can see [this post](https://stackoverflow.com/questions/5225416/convert-linq-to-sql-expression-to-expression-tree) for a good general example, which you should be able to adapt to your case. – StriplingWarrior Sep 19 '17 at 16:17