【问题标题】:How does nesting an OrderBy in a Dynamic Linq query work?在动态 Linq 查询中嵌套 OrderBy 是如何工作的?
【发布时间】:2014-11-21 02:33:17
【问题描述】:

我正在使用 Dynamic Linq,今天我想构建一个稍微复杂一点的嵌套查询:

"Composition
.Where(((ExpirationDate > DateTime.UtcNow.Date) && (ExpirationDate.Year != 9999)))
.OrderBy(\"ExpirationDate ASC\")
.Select(ExpirationDate)
.FirstOrDefault() == @0"

(中断只是为了这篇文章的可读性,而不是真正存在于代码中)

查询由一个字符串变量保存并传递给这个:

private static Func<IQueryable<T>, object, IQueryable<T>> CreateWhereExpression<T>(string whereClause) where T : class
{
     return (q, o) => q.Where(whereClause, o);
}

这很高兴创建了 Where 表达式。 (请注意 whereClause 包含“Composition.Where....”上方的确切字符串) 但是一到执行的时间,它就会报错:

不存在适用的聚合方法“OrderBy”

所以我的问题是,我做错了什么?如何让嵌套的 OrderBy 工作?

【问题讨论】:

  • 您是否要解析LINQ?动态 LINQ 不支持解析自己的语法。
  • 是的,我正在尝试让 Dynamic Linq 将字符串解析为 Linq 查询。我也尝试过使用 Linq 语法 '.OrderBy(ExpirationDate)' 但我得到了同样的错误。我正在尝试完成与此类似的事情:stackoverflow.com/questions/10314708/… 但是使用 orderby 查询。

标签: c# linq dynamic-linq


【解决方案1】:

默认情况下,DynamicLinq 支持对IEnumerable 字段进行嵌套查询的一些函数,所有这些函数都在接口IEnumerableSignatures 中定义,如WhereAnyCount 等,但没有OrderbySelectFirstOrDefault 您需要什么。
所以你可以像

一样将它添加到这个界面中
interface IEnumerableSignatures
{
    ....
    void OrderBy(object selector);
    void Select(object selector);
    void FirstOrDefault();
}

之后你需要像这样修复ParseAggregate方法

Expression ParseAggregate(Expression instance, Type elementType, string methodName, int errorPos)
{
    ....
    if (signature.Name == "Min" || signature.Name == "Max" 
        || signature.Name == "OrderBy" || signature.Name == "Select" //add this for support OrderBy and Select that need two generic parameters
    )
    ....
}

最后下一个查询将起作用

"Composition
.Where((ExpirationDate > DateTime.UtcNow.Date) && (ExpirationDate.Year != 9999))
.OrderBy(ExpirationDate)
.Select(ExpirationDate)
.FirstOrDefault() == @0"

【讨论】:

  • +1。我使用的 DynamicLinq 版本从 Nuget 中消失了,我不得不引入基本版本,这显然缺少此功能。谢谢!
猜你喜欢
  • 1970-01-01
  • 2017-04-28
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2012-05-06
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多