简体   繁体   English

在子查询中使用 FirstOrDefault

[英]Using FirstOrDefault in a sub query

We are having major performance issues with some of our LINQ-to-SQL queries.我们的一些 LINQ-to-SQL 查询存在重大性能问题。

We have a Case table, with a one-to-many relationship on CaseStatus (relationship table is CaseCaseStatus) Although, we want to keep track of all statusses on a case, only the last one really has any value.我们有一个 Case 表,在 CaseStatus 上有一对多的关系(关系表是 CaseCaseStatus) 虽然我们想跟踪一个案例的所有状态,但只有最后一个真正有价值。

We are building a query like follows:我们正在构建如下查询:

IQueryable<Case> results = Repository.GetFullList(); // Returns a Queryable

if(filter.OnlyOpen){
   results = results
      .Where(c => c.CaseCaseStatusses.Any() 
               && c.CaseCaseStatusses.OrderByDescending(cs => cs.Timestamp).FirstOrDefault().Status.IsClosed != true);
}

results.Select(x => Dto(x)).ToList();

Basicly we want to know if the last status, has a property "IsClosed == true".基本上我们想知道最后一个状态是否有一个属性“IsClosed == true”。

When I monitor my database through the SQL profiler, I can see that the database is being queried when we hit the Select statement, not before.当我通过 SQL 分析器监视我的数据库时,我可以看到当我们点击 Select 语句时正在查询数据库,而不是之前。 (As intented) But while the query is being executed, I can see a select query for each case: (按原意)但是在执行查询时,我可以看到每个案例的 select 查询:

SELECT [cs0].[Id], [cs0].[CaseId], [cs0].[Note], [cs0].[ShowOnClientPage], [cs0].[StatusId], [cs0].[TimestampUTC], [cs.Status0].[IsClosed] 
FROM [CaseCaseStatusses] AS [cs0] 
INNER JOIN [CaseStatusses] AS [cs.Status0] ON [cs0].[StatusId] = [cs.Status0].[Id]
WHERE [cs0].[CaseId] = <CaseId>

Since we have 8000+ records in our Case Table, it does 8000 of above select statements... while we want 1 single query to be executed.由于我们的案例表中有 8000 多条记录,它执行 8000 条以上 select 语句......而我们希望执行 1 个单个查询。 Has this behavior changed in EFCore? EFCore 中的这种行为是否发生了变化? I could swear I've done this before and it would output a single query (granted, it was a big unreadable query and not EFCore)我可以发誓我以前做过这个,它会 output 单个查询(当然,这是一个不可读的大查询,而不是 EFCore)

Is there another (better) way to perform these kind of queries?是否有另一种(更好的)方法来执行这类查询?

Try this query, it should work with any EF version.试试这个查询,它应该适用于任何 EF 版本。

var results = 
   from r in results
   from c in r.CaseCaseStatusses
      .OrderByDescending(cs => cs.Timestamp)
      .Take(1)
   where c != null && c.Status.IsClosed != true
   select r;

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM