使用动态OrderBy进行分页/分页的Linq表达式

时间:2011-04-13 16:33:46

标签: .net linq .net-4.0 pagination entity-framework-4.1

所有

我正在尝试使用网格进行分页。为了做到这一点,我必须传入哪个字段进行排序。我无法弄清楚如何使用Linq查询执行此操作。我使用的是.NET 4 / EF 4.1。在下面的两个例子中,#1工作正常。问题是,我在现场传递以进行排序,因此我需要能够动态地更改我们正在排序的内容。当我尝试使用示例2中的字符串时,它不会按我的表达式排序。有没有办法实现这个目标?似乎很多人都需要这个功能。

    [Example 1]
(from e in _context.MyEntity
 where (MyWhereClause)
 orderby e.SomeProperty Ascending
 select e).Skip(Offset).Take(MyCountPerPage);

    [Example 2]
(from e in _context.MyEntity
 where (MyWhereClause)
 orderby "SomeField, ASC"
 select e).Skip(Offset).Take(MyCountPerPage);

-Thanks -

4 个答案:

答案 0 :(得分:4)

使用Dynamic LINQ

答案 1 :(得分:1)

首先,您需要从查询中提取您的订单并使用扩展方法版本

var query = from e in _context.MyEntity
            where (MyWhereClause)
            select e;

query = query.DynamicOrderBy("property");

query = query.Skip(Offset).Take(MyCountPerPage);

接下来,我们必须构建DynamicOrderBy,我假设查询是针对某种IQueryable<T>

//Need this to construct the query correctly
static MethodInfo s_orderBy = typeof(Queryable).GetMethods().First(m => m.Name == "OrderBy");

static IOrderedQueryable<T> DynamicOrderBy<T>(this IQueryable<T> source, string property)
{
    var expr = source.Expression;
    var p = Expression.Parameter(typeof(T), "x");
    var propInfo = typeof(T).GetProperty(property, BindingFlags.Public | BindingFlags.Instance | BindingFlags.IgnoreCase);
    var sortExpr = Expression.Lambda(Expression.Property(p, propInfo), p)
    var method = s_orderBy.MakeGenericMethod(typeof(T), propInfo.PropertyType);
    var call = Expression.Call(method, expr, sortExpr);
    var newQuery = source.Provider.CreateQuery<T>(call);
    return newQuery as IOrderedQueryable<T>;
}

答案 2 :(得分:0)

我想,你需要这个jqGrid。我在the answer之前发布了完整的VS2008 project,您可以将其作为示例。

主要思想是Entity Framwork可以与ObjectQuery<T>一起使用,它支持您需要的“SomeField,ASC”排序。因此,您可以实现所有您需要的而无需动态LINQ扩展。更多(见here)你可以使用像

这样的结构
.Where("it.equipmentID < @maxId", new ObjectParameter ("maxId", 100))

WHERE有字符串参数(“it.equipmentID&lt; @maxId”)。因此,您可以使用jqGrid所需的字符串参数实现所有分页,排序和过滤。我开始回答的例子演示了如何做到这一点。

答案 3 :(得分:-2)

   var query = (from e in _context.MyEntity
     where (MyWhereClause)
     orderby e.SomeProperty Ascending
     select e).Skip(Offset).Take(MyCountPerPage);

    if(Ascendingflag)
       query = query.OrderBy(a = > SortExpression);
    else
       query = query.OrderByDescending(a = > SortExpression);