【发布时间】:2016-11-15 22:15:40
【问题描述】:
我经常在 LINQ for Entity Framework 中遇到一种模式,如果指定了字符串值,我会在其中添加 .Where 子句,例如:
IQueryable<Foo> query = Foos.AsQueryable()
if (!string.IsNullOrWhitespace(nameFilter)) query = query.Where(x => x.Name == name);
if (!string.IsNullOrWhitespace(addressFilter) != null) query = query.Where(x => x.Address == addressFilter );
if (!string.IsNullOrWhitespace(cityFilter) != null) query = query.Where(x => x.City == cityFilter );
// ...
我想清理它并避免重复过滤器。我想我可以创建一个扩展方法:
public static IQueryable<T> WhereEqualIfSpecified<T>(
this IQueryable<T> query,
Expression<Func<T, string>> fieldDelegate,
string filterValue)
{
return string.IsNullOrWhiteSpace(filterValue)
? query
: query.Where(x => fieldDelegate(x) == filterValue); // not valid, see question below
}
这样我就可以将代码改为:
IQueryable<Foo> query = Foos.AsQueryable()
.WhereEqualIfSpecified(x => x.Name, nameFilter)
.WhereEqualIfSpecified(x => x.Address, addressFilter)
.WhereEqualIfSpecified(x => x.City, cityFilter)
// ...
;
但我发现,在上面的 WhereEqualIfSpecified 方法中,fieldDelegate 必须编译为 Func() 才能针对实体源调用,这破坏了执行这些步骤的意义,这些步骤将在我原始代码中的数据库。
我错过了如何从fieldDelegate 创建一个可以进行比较的新Expression 的最后一步,而不仅仅是返回字符串值。这种方法会奏效吗?如何在WhereEqualIfSpecified 中设置必要的Expression 以允许LINQ-to-Entities 稍后执行?
【问题讨论】:
标签: c# entity-framework linq expression-trees