【发布时间】:2015-06-10 22:17:25
【问题描述】:
我有一个调用实体框架函数的方法。它负责发送“select 子句”、“order by 子句”和可能的包含(考虑到我正在使用延迟加载)。该方法如下所示:
public IEnumerable<TReturn> GetAll<TReturn, TOrderKey>(
Expression<Func<TEntity, TReturn>> selectExp,
Expression<Func<TEntity, TOrderKey>> orderbyExp,
Boolean descending,
params Expression<Func<TEntity, Object>>[] includeExps)
{
var query = DbSet.AsQueryable();
query = !descending ? query.OrderBy(orderByExp) : query.OrderByDescending(orderByExp);
if (includeExps != null)
query = includeExps.Aggregate(query, (current, exp) => current.Include(exp));
return query.Select(selectExp).ToList();
}
当我打电话时:
_service.GetAll(i => new { i.Name}, i => i.Name, false, null);
效果很好!那就是生成的 SQL 正是我想要的。
但是,考虑到一个真实的场景(在我的例子中,我使用的是 asp.net mvc),我有一个从客户端获取 order 参数的 Action 方法。
就是方法:
public JsonResult GetAllUsers(string sortColumn, bool sortDescending)
{
//sortColumn string must be translated in a Expression
var users = _service.GetAll(i => new { i.Name, i.Email }, i => i.Name, sortDescending, null);
//
//
}
我的第一次尝试是为每一列创建一个表达式,如下所示:
public JsonResult GetAllUsers(string sortColumn, bool sortDescending)
{
//I don't what is the Type that I should put here
//It can be anything, like: Expression<Func<User, String>>,
//Expression<Func<User, Guid>>, Expression<Func<User, Int>>
?Type? orderExp;
switch(sortColumn)
{
case "UserId":
//Expression<Func<User, Guid>>
orderExp = i => i.UserId;
break;
case "Name":
//Expression<Func<User, String>>
orderExp = i => i.Email;
break;
}
//sortColumn string must be translated in a Expression
var users = _service.GetAll(i => new { i.Name, i.Email }, orderExp, sortDescending, null);
//
//
}
我想创建一个基于 sortProperty 的表达式,stackoverflow 上有很多关于它的信息,但是(请参阅操作方法)必须在处理之前键入变量。不能在每个“案例”中调用 GetAll 方法,因为它返回一个匿名类型。
我无法将所有列都转换为Expression<Func<User, Object>>,因为实体框架不支持它。
Linq.Dynamic 应该有帮助,但我不想使用字符串参数。
【问题讨论】:
-
你的问题到底是什么?如果您不能在第一次尝试时将您的问题陈述为问题,那么您将被否决并关闭。
-
对不起...我认为还不够清楚。我想根据属性名称创建一个表达式,stackoverflow 上有很多关于它的信息,但是(请参阅操作方法)必须在处理之前键入变量。 GetAll 返回一个匿名类型,应该在方法结束时调用。
-
所以你想要一个谓词构建器,除了你想根据它排序和/或选择数据子集(有一个函数,而不是一个谓词)。考虑一下:stackoverflow.com/a/3291811/1144090 - 告诉我们不能按列号排序,这是我想将列名转换成的。或者,使用Telerik :)
-
我可以使用 Func,但它们不会被翻译成 SQL。 Func 在数据加载到内存后运行。
-
你可以在这里stackoverflow.com/a/18321266/1479335找到如何按列名排序。严格来说不是你想要的,但我想至少可以应用于排序。
标签: c# linq entity-framework