C# Linq实体框架——我可以使用递归方法吗?

C# Linq实体框架——我可以使用递归方法吗?,c#,entity-framework,linq-to-entities,C#,Entity Framework,Linq To Entities,下面是我对上一个问题的精彩回答: 我现在试图理解如何将递归之类的东西应用到我的解决方案中 概括地说,不是此方法的多个类似声明,而是: protected IQueryable<Database.Product> GetActiveProducts( ObjectSet<Database.Product> products ) { var allowedStates = new string[] { "Active" , "Pending" }; re

下面是我对上一个问题的精彩回答:

我现在试图理解如何将递归之类的东西应用到我的解决方案中

概括地说,不是此方法的多个类似声明,而是:

protected IQueryable<Database.Product> GetActiveProducts( ObjectSet<Database.Product> products ) {

    var allowedStates = new string[] { "Active" , "Pending" };

    return (
        from product in products
        where allowedStates.Contains( product.State )
            && product.Hidden == "No"
        select product
    );

}
在本例中,我希望Orders EntityCollection也通过GetActiveEntities()进行过滤,以便返回的最新订单永远不会是“隐藏”订单

是否可以对实现IHideable的所有EntityCollection进行过滤?可能是通过在GetActiveEntities()中应用一些反射/递归并调用自身?我之所以说递归,是因为最好的解决方案会深入到实体图的多个层次

这玩意儿真让我头疼

更新#1(将我的评论移至此处)

谢谢你,史蒂夫

使该方法按建议可接受会产生以下错误:

'System.Data.Objects.DataClasses.EntityCollection<Database.Order>' does not contain a definition for 'GetActiveEntities' and no extension method 'GetActiveEntities' accepting a first argument of type 'System.Data.Objects.DataClasses.EntityCollection<Database.Order>' could be found (are you missing a using directive or an assembly reference?)

我还尝试在EntityCollection上调用AsQueryable()并返回IQueryable,但返回了相同的错误。

编辑为使用ObjectSet而不是EntityCollection

我建议使用我的解决方案,但作为扩展方法,可以应用于任何查询:

public static IQueryable<TEntity> WhereActive<TEntity>(
    this IQueryable<TEntity> entities)
    where TEntity : class , Database.IHideable
{
    var allowedStates = new string[] { "Active", "Pending" };

    return (
        from entity in entities
        where allowedStates.Contains(entity.State)
            && entity.Hidden == "No"
        select entity
    );
}  

谢谢你的回复,斯蒂芬。实际上,我在今天早些时候将该方法重构为一个扩展方法,但不想让这个示例陷入困境,所以使用了一个方法调用。很高兴知道这是正确的举动-很多C语言功能对我来说都是新的。感谢Steve,我将我的评论移到了问题区域以便于阅读…你是对的:
EntityCollection
没有实现
IQueryable
。我已经更新了我的答案,使用了
实体.Orders
,而不是
产品.Orders
,这应该是可行的。(我还将
latestOrder
计算更改为使用
orderby
)。
'System.Data.Objects.DataClasses.EntityCollection<Database.Order>' does not contain a definition for 'GetActiveEntities' and no extension method 'GetActiveEntities' accepting a first argument of type 'System.Data.Objects.DataClasses.EntityCollection<Database.Order>' could be found (are you missing a using directive or an assembly reference?)
LINQ to Entities does not recognize the method 'System.Collections.Generic.IEnumerable`1[Database.Order] GetActiveEntities[Order](System.Data.Objects.DataClasses.EntityCollection`1[Database.Order])' method, and this method cannot be translated into a store expression.
public static IQueryable<TEntity> WhereActive<TEntity>(
    this IQueryable<TEntity> entities)
    where TEntity : class , Database.IHideable
{
    var allowedStates = new string[] { "Active", "Pending" };

    return (
        from entity in entities
        where allowedStates.Contains(entity.State)
            && entity.Hidden == "No"
        select entity
    );
}  
var products = Entities.Products.WhereActive();

return (

    from product in products

    let latestOrder = (
        from order in Entities.Orders.WhereActive()
        where order.ProductId == product.Id
        orderby candidateOrder.Date descending
        select order).FirstOrDefault()

    select new Product()
    {
        Id = product.Id,
        Name = product.Name,
        LatestOrder = new Order()
        {
            Id = latestOrder.Id,
            Amount = latestOrder.Amount,
            Date = latestOrder.Date
        }
    }
);