C# 基于表达式树的动态查询

C# 基于表达式树的动态查询,c#,expression-trees,dynamic-linq,C#,Expression Trees,Dynamic Linq,我有一个表单,用户将从下拉列表中选择以下内容: table_name columnName_to_sort_by columnName_to_search_in 用户应在文本框中输入Search\u text 表格应从多个表格中提取数据。我希望避免为每个表编写排序和搜索每个字段。这就是我想使用表达式树的原因。我想动态地构建查询 我想编写一个通用方法,根据用户输入为select、where和orderby方法生成表达式树。我可以使用System.Reflection获取被查询的类型(

我有一个表单,用户将从下拉列表中选择以下内容:

  table_name
  columnName_to_sort_by
  columnName_to_search_in
用户应在文本框中输入
Search\u text

表格应从多个表格中提取数据。我希望避免为每个表编写排序和搜索每个字段。这就是我想使用表达式树的原因。我想动态地构建查询

我想编写一个通用方法,根据用户输入为
select
where
orderby
方法生成表达式树。我可以使用
System.Reflection
获取被查询的
类型(我所有的表都是类型-我使用的是LinqToSql)

我不知道如何形成表达式树

以下是我目前掌握的情况:

private static List<T> GetSortedData<T>( string sortColumnName) 
{ 
        var type = typeof(T); 
        var property = type.GetProperty(sortColumnName); 
        var parameter = Expression.Parameter(type, "p"); 
        var propertyAccess = Expression.MakeMemberAccess(parameter, property); 
        var orderByExp = Expression.Lambda(propertyAccess, parameter); 
        MethodCallExpression resultExp = Expression.Call(typeof(Queryable), "OrderBy", new Type[] { type, property.PropertyType }, WHAT_SHOULD_BE_HERE, Expression.Quote(orderByExp)); 
        return (List<T>)Expression.Lambda(resultExp).Compile().DynamicInvoke(); 
} 
私有静态列表GetSortedData(字符串sortColumnName)
{ 
var类型=类型(T);
var property=type.GetProperty(sortColumnName);
var参数=表达式参数(类型为“p”);
var propertyAccess=Expression.MakeMemberAccess(参数,属性);
var orderByExp=Expression.Lambda(propertyAccess,参数);
MethodCallExpression resultExp=Expression.Call(typeof(Queryable),“OrderBy”,新类型[]{Type,property.PropertyType},这里应该是什么,Expression.Quote(orderByExp));
return(List)Expression.Lambda(resultextp.Compile().DynamicInvoke();
} 

如何使用表达式树动态实现
select
sort
orderby
。当您问“这里应该是什么”时,您很好奇使用什么表达式来指示OrderBy的“源”参数,当用作扩展方法时,它通常由操作数暗示。您需要做的是将示例更改为在IQueryable上操作,并且需要接受它作为输入参数。另外,将您的WHAT_SHOULD_HERE占位符替换为“list.Expression”,如下所示

private static IEnumerable<T> GetSortedData<T>(IQueryable<T> list, string sortColumnName) 
{ 
    var type = typeof(T); 
    var property = type.GetProperty(sortColumnName); 
    var parameter = Expression.Parameter(type, "p"); 
    var propertyAccess = Expression.Property(parameter, property); 
    var orderByExp = Expression.Lambda(propertyAccess, parameter); 
    MethodCallExpression resultExp = Expression.Call(typeof(Queryable), "OrderBy", new[] { type, property.PropertyType }, list.Expression, Expression.Quote(orderByExp)); 
    return (IEnumerable<T>)Expression.Lambda(resultExp).Compile().DynamicInvoke(); 
} 

我在订购时遇到了同样的错误


我查看了
调用
方法,发现缺少参数--
list.Expression
,其中list是您的
IQuerable

,可以通过任何方式对多个列进行排序
static void Main(string[] args)
{
    var list = new List<Person>(new[] 
    { 
        new Person { FirstName = "John" }, 
        new Person { FirstName = "Jane" }
    }).AsQueryable();

    foreach (var o in GetSortedData(list, "FirstName")) 
        Console.WriteLine(o.FirstName);
}

public class Person
{
    public string FirstName { get; set; }
}
Jane
John