c# - 如何在 EF Where() 子句中使用 Predicate<T>?

标签 c# linq entity-framework linq-expressions

我正在尝试在我的 EF 过滤代码中使用谓词。

这个有效:

IQueryable<Customer> filtered = customers.Where(x => x.HasMoney && x.WantsProduct);

但是这个:

Predicate<T> hasMoney = x => x.HasMoney;
Predicate<T> wantsProduct = x => x.WantsProduct;
IQueryable<Customer> filtered = customers.Where(x => hasMoney(x) && wantsProduct(x));

运行时失败:

The LINQ expression node type 'Invoke' is not supported in LINQ to Entities.

我不能使用第一个选项,因为这是一个简单的示例,实际上,我正在尝试将一堆谓词组合在一起(使用 and、not、or 等)来实现我想要的.

如何让 EF Linq 提供程序“理解”我的谓词?

如果我使用 Func<T, bool>,我会得到相同的结果.它适用于 Expression<Func<T>> , 但我不能将表达式组合在一起进行复杂的过滤。如果可能,我宁愿避免使用外部库。

更新:
如果无法做到这一点,我有什么选择?也许表达式以某种方式组合/或'ed/and'以达到相同的效果?

最佳答案

Expression<Func<Customer, bool>> hasMoney = x => x.HasMoney;
Expression<Func<Customer, bool>> wantsProduct = x => x.WantsProduct;
IQueryable<Customer> filtered = customers.Where(hasMoney).Where(wantsProduct);
  • 使用Expression<T>离开x => x.HasMoney作为表达式树,而不是将其编译为 .NET 方法
  • 使用Expression<Func<Customer, bool>>而不是 Expression<Predicate<Customer>> ,因为这就是 Queryable.Where 期待
  • 直接传入 .Where ,使用多个 .Where 组合它们调用而不是 && .

通过使用 .Union 重写更复杂的条件(包括 not 或 or 等​​)是可能的。 , .Except

另一种方法是使用 LINQKitAsExpandable :

Expression<Func<Customer, bool>> hasMoney = x => x.HasMoney;
Expression<Func<Customer, bool>> wantsProduct = x => x.WantsProduct;
IQueryable<Customer> filtered = customers.AsExpandable().Where(x => hasMoney.Invoke(x) && wantsProduct.Invoke(x));

关于c# - 如何在 EF Where() 子句中使用 Predicate<T>?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/13390126/

相关文章:

c# - Automapper 5.0.0 缺少 SourceValue(自定义转换器)

c# - LINQ 如果 .Any 匹配 .Any

.net - Entity Framework 何时填充导航属性?

entity-framework - 如何从 Entity Framework 中的关系对象获取数据?

c# - 为什么在 C# 中使用简单属性而不是字段?

c# - 如何获取RadTreeView的点击节点文本

c# - 如何使用 LINQ 匹配两个相同的数据库表?

c# - 如何在两个SQL Server表之间检索审核跟踪,然后以正确的顺序放回它们?

c# - AsNoTracking 使用 LINQ 查询语法而不是方法语法

c# - 未经检查的 block 不适用于 BigInteger?