2010-04-15 26 views
3

我对由对象字段排序泛型列表的方法:创建排序功能的通用列表

public static IQueryable<T> SortTable<T>(IQueryable<T> q, string sortfield, bool ascending) 
{ 
    var p = Expression.Parameter(typeof(T), "p"); 

    if (typeof(T).GetProperty(sortfield).PropertyType == typeof(int?)) 
    { 
     var x = Expression.Lambda<Func<T, int?>>(Expression.Property(p, sortfield), p); 
     if (ascending) 
      q = q.OrderBy(x); 
     else 
      q = q.OrderByDescending(x); 
    } 
    else if (typeof(T).GetProperty(sortfield).PropertyType == typeof(int)) 
    { 
     var x = Expression.Lambda<Func<T, int>>(Expression.Property(p, sortfield), p); 
     if (ascending) 
      q = q.OrderBy(x); 
     else 
      q = q.OrderByDescending(x); 
    } 
    else if (typeof(T).GetProperty(sortfield).PropertyType == typeof(DateTime)) 
    { 
     var x = Expression.Lambda<Func<T, DateTime>>(Expression.Property(p, sortfield), p); 
     if (ascending) 
      q = q.OrderBy(x); 
     else 
      q = q.OrderByDescending(x); 
    } 
    // many more for every type 
    return q; 
} 

有什么方法可以让我崩溃的IFS到一个通用的声明? 主要问题是,对于部分 Expression.Lambda<Func<T, int>> 我不知道如何一般地写它。

+0

http://stackoverflow.com/questions/41244/dynamic-linq-orderby – 2010-04-15 15:48:57

回答

3

如果展开Queryable.OrderBy它的定义,那么你不必使用Expression.Lambda通用超载:

public static IQueryable<T> SortTable<T>(
    IQueryable<T> q, string sortfield, bool ascending) 
{ 
    var p = Expression.Parameter(typeof(T), "p"); 
    var x = Expression.Lambda(Expression.Property(p, sortfield), p); 

    return q.Provider.CreateQuery<T>(
       Expression.Call(typeof(Queryable), 
           ascending ? "OrderBy" : "OrderByDescending", 
           new Type[] { q.ElementType, x.Body.Type }, 
           q.Expression, 
           x)); 
} 
0

不会在工作?

public static IQueryable<T> SortTable<T>(IQueryable<T> q, string sortfield, bool ascending) 
    { 
     var type = typeof(T).GetProperty(sortfield).PropertyType; 
     var p = Expression.Parameter(typeof(T), "p"); 
     var x = Expression.Lambda<Func<T, type> >(Expression.Property(p, sortfield), p); 
     if (ascending) 
      q = q.OrderBy(x); 
     else 
      q = q.OrderByDescending(x); 
     return q; 
    } 
+0

'type'不是一个类型变量(如'T'),所以这将无法工作。 – dtb 2010-04-15 15:54:03

+0

在System.Reflection中有一个方法可以返回'Func '类型,但是,我确定... – Noldorin 2010-04-15 15:55:23

+0

@Noldorin:你的意思是'typeof(Func <,>).MakeGenericType(typeof(T),type)' ?但是,如果没有反射,你仍然不能使用结果来调用'Expression.Lambda '。 – dtb 2010-04-15 15:56:44