【发布时间】:2015-05-22 18:28:54
【问题描述】:
这个问题已经在一定程度上讨论了这个问题:Create Generic Expression from string property name 但也许我错过了答案,或者它是微妙的不同。
我有以下可查询的扩展方法:
public static IQueryable<TSource> OrderByPropertyDescending<TSource>(IQueryable<TSource> source, string propertyName)
{
var sourceType = typeof (TSource);
var parameter = Expression.Parameter(sourceType, "item");
var orderByProperty = Expression.Property(parameter, propertyName);
var orderBy = Expression.Lambda(orderByProperty, new[] { parameter });
return Queryable.OrderByDescending(source, (dynamic) orderBy);
}
为了解决这个问题,让我们假设可查询的源实例有一个名为“Created”的属性,它是 DateTime 的一种类型。如果我们定义一个具有“Created”属性的类,然后使用 OrderByDescending,那么上面的方法就可以正常工作。例如
var queryable = new List<EntityClassWithCreatedProperty>().AsQueryable();
var result = queryable.OrderByPropertyDescending("Created").ToList();
如果我们做同样的事情,但使用 ICreated 之类的接口,它上面有 Created 属性:
public interface ICreated
{
DateTime Created { get; }
}
那么以下也可以:
var queryable = new List<ICreated>().AsQueryable();
var result = queryable.OrderByPropertyDescending("Created").ToList();
但是,如果您具有以下接口层次结构:
public interface ITimestamped : ICreated
{
...
}
那么下面会失败:
var queryable = new List<ITimestamped>().AsQueryable();
var result = queryable.OrderByPropertyDescending("Created").ToList();
与另一个问题的错误消息类似:实例属性“已创建”未为类型 ITimestamped 定义。我假设我需要在声明类型的接口上找到属性(我可以通过爬取源类型来做到这一点),但是我该怎么处理它呢?我尝试过的大多数尝试都导致不正确的原始源类型无法转换回 IQueryable。我需要在某处使用 ConvertType 调用吗?谢谢。
【问题讨论】:
标签: c# expression-trees