我可以在Entity Framework SubQuery中使用扩展方法吗?
我正在尝试使用Entity Framework整合访问不同表的逻辑。 我创建了一个扩展方法,用于从我的注册实体中提取所有注册人:
public static IEnumerable Attending(this IEnumerable registrations) { return registrations.Where(r => r.Status == RegistrationStatus.Paid || r.Status == RegistrationStatus.Assigned || r.Status == RegistrationStatus.Completed); }
这适用于这样的查询:
var attendees = db.Registrations.Attending().ToList();
但是在子查询中使用它时不起作用:
ProductTotals = db.Products.Where(p => p.EventID == ev.Id).Select(p => new ProductSummaryViewModel { ProductID = p.ProductID, ProductName = p.Name, Registrations = p.Registrations.Attending().Count(), }).ToList();
我收到以下错误:
LINQ to Entities无法识别方法’System.Collections.Generic.IEnumerable
1[Registration] Attending(System.Collections.Generic.IEnumerable
1 [Registration])’方法,并且此方法无法转换为商店表达式。
有没有办法在子查询中重用该代码?
您要实现的主要function是重用定义Attending
含义的谓词。 您可以通过将表达式存储在一个只读变量中来实现,该变量可供应用程序中需要它的任何人使用,例如在静态类ExpressionConstants
。
public static readonly Expression> IsAttending = r => r.Status == RegistrationStatus.Paid || r.Status == RegistrationStatus.Assigned || r.Status == RegistrationStatus.Completed;
那你可以做
var attendees = db.Registrations.Where(ExpressionConstants.IsAttending).ToList();
并在子查询中使用:
ProductTotals = db.Products.Where(p => p.EventID == ev.Id).Select(p => new ProductSummaryViewModel { ProductID = p.ProductID, ProductName = p.Name, Registrations = p.Registrations.AsQueryable() // AsQueryable() .Where(ExpressionConstants.IsAttending).Count(), })
AsQueryable()
是必需的,因为p.Registrations
可能是ICollection
。