EF5代码首先排序嵌套项

时间:2013-08-01 15:19:52

标签: ef-code-first entity-framework-5 nested-queries

在使用Entity Framework 5 Code First检索一组数据时,我遇到了一个小问题。这是我的代码:

var data = context.Customers
            .Include("Orders")
            .Include("Orders.Items")
            .Include("Orders.Items.Article").ToArray();
foreach (var customer in data)
{
    customer.Orders = customer.Orders.OrderByDescending(o => o.OrderDate).ToArray();
}

这是有效的(哇!)。但是,我正试图将foreach从那里拿出来,我希望数据库引擎继续负责处理数据。我该怎么做呢?

我尝试过这种类型的加入:

var data = from customer
           in context.Customers
           select new {
               customer.Id,
               customer.Name,
               // customer.Orders below doesn't have an Include() to include order items
               Orders = customer.Orders.OrderByDescending(b => b.OrderDate)
           };

// Translate anonymous object to actual models
var customers = new List<CustomerModel>();
foreach (var customer in data)
{
    customers.Add(new CustomerModel()
    {
        Id = customer.Id,
        Name = customer.Name,
        Orders = customer.Orders.ToArray()
    });
}

但是,正如评论所说,customer.Orders没有Include()方法来包含属于这些项目的项目和文章。然后我尝试从context而不是customer对象进入:

Orders = context.Orders.Include("Items").Where(o => o.Id == customer.Id)

但这会导致运行时异常Include()无法以这种方式使用(在嵌套查询中?):

Method 'System.Data.Entity.Infrastructure.DbQuery`1[MyTests.Models.OrderModel] Include(System.String)' declared on type 'System.Data.Entity.Infrastructure.DbQuery`1[MyTests.Models.OrderModel]' cannot be called with instance of type 'System.Data.Objects.ObjectQuery`1[MyTests.Models.OrdersModel]'

这样的事情是否可能,像这样嵌套?

如何让数据库处理数据而不是在我的第一个代码块中使用foreach

提前致谢。

JP

2 个答案:

答案 0 :(得分:1)

您可以尝试此查询:

List<CustomerModel> customers =
           (from customer
            in context.Customers
            select new {
                customer.Id,
                customer.Name,
                Orders = customer.Orders
                    .OrderByDescending(o => o.OrderDate)
                    .Select(o => new {
                        Order = o,
                        Items = o.Items
                            .Select(i => new {
                                Item = i,
                                Article = i.Article
                            })
                    })
           })
           .AsEnumerable()
           .Select(x => new CustomerModel
           {
               Id = x.Id,
               Name = x.Name,
               Orders = x.Orders.Select(o => o.Order).ToArray()
           })
           .ToList();

虽然未使用内部匿名对象中的ItemArticle,但它们将被加载,而Entity Framework的关系修复应为{{1}设置正确的导航属性}和Order.Items - 只要关系不是多对多而您不使用Item.Article

如果要将此作为无跟踪查询执行,则基本上必须自己设置导航属性。应该可以在AsNoTrackingSelect之间移动以下额外AsEnumerable()

Select(...)

答案 1 :(得分:0)

这应该适合你:

var os = new DbContext().Orders;

var data = from customer
       in context.Customers
       select new {
           customer.Id,
           customer.Name,

           Orders = os.Include("Items").Include("Items.Article")
               .Where(o => o.CustomerId == id)
               .OrderByDescending(b => b.DatumAangemaakt)
       };