Logsエンティティがあり、そこから2つの継承されたエンティティがあります。継承された各エンティティは、別の異なるエンティティにリンクします。ResponseLogとSessionLogは、それぞれResponseエンティティとSessionエンティティに接続します。
Logsテーブルには70万をはるかに超えるレコードがあり、数百万に成長すると予想されます。
私がやりたいのは、ログテーブルから上位100のエントリを取得し、それらをリストに入れることです。
var LogResults = (from entries in this.DbContext.LogEntries
orderby entries.TimeStamp descending
select entries).Take(nEntries);
ただし、これを行うとList<LogEntry> LogResultList= LogResults.ToList();
、完了するまでに約45秒かかります。'ToList'関数は、データベースとのトランザクションが実際に行われるときのものであることに気付きましたが、nEntries = 100、25、または10000のいずれであっても、かかる時間は同じです。
linqが生成するクエリを調べたところ、上位100を取得する前に、ログテーブル内のすべてのログエントリ(700k +)のタイプを評価しているようです。
トップ100を取得し、それらのレコードだけが継承されたタイプを特定する方法はありますか?
生成されるSQLは次のとおりです。
SELECT TOP (100)
[Project3].[C1] AS [C1],
[Project3].[Id] AS [Id],
[Project3].[Message] AS [Message],
[Project3].[TimeStamp] AS [TimeStamp],
[Project3].[UserId] AS [UserId],
[Project3].[SeverityLevelRaw] AS [SeverityLevelRaw],
[Project3].[C2] AS [C2],
[Project3].[C3] AS [C3]
FROM ( SELECT
[Extent1].[Id] AS [Id],
[Extent1].[Message] AS [Message],
[Extent1].[TimeStamp] AS [TimeStamp],
[Extent1].[UserId] AS [UserId],
[Extent1].[SeverityLevelRaw] AS [SeverityLevelRaw],
CASE WHEN ( NOT (([Project1].[C1] = 1) AND ([Project1].[C1] IS NOT NULL))) THEN '0X' WHEN (([Project1].[C1] = 1) AND ([Project1].[C1] IS NOT NULL) AND ( NOT (([Project2].[C1] = 1) AND ([Project2].[C1] IS NOT NULL)))) THEN '0X0X' ELSE '0X0X0X' END AS [C1],
CASE WHEN ( NOT (([Project1].[C1] = 1) AND ([Project1].[C1] IS NOT NULL))) THEN CAST(NULL AS uniqueidentifier) WHEN (([Project1].[C1] = 1) AND ([Project1].[C1] IS NOT NULL) AND ( NOT (([Project2].[C1] = 1) AND ([Project2].[C1] IS NOT NULL)))) THEN [Project1].[SessionId] ELSE [Project1].[SessionId] END AS [C2],
CASE WHEN ( NOT (([Project1].[C1] = 1) AND ([Project1].[C1] IS NOT NULL))) THEN CAST(NULL AS uniqueidentifier) WHEN (([Project1].[C1] = 1) AND ([Project1].[C1] IS NOT NULL) AND ( NOT (([Project2].[C1] = 1) AND ([Project2].[C1] IS NOT NULL)))) THEN CAST(NULL AS uniqueidentifier) ELSE [Project2].[ResponseId] END AS [C3]
FROM [dbo].[LogEntries] AS [Extent1]
LEFT OUTER JOIN (SELECT
[Extent2].[SessionId] AS [SessionId],
[Extent2].[Id] AS [Id],
cast(1 as bit) AS [C1]
FROM [dbo].[LogEntries_RuntimeLogEntry] AS [Extent2] ) AS [Project1] ON [Extent1].[Id] = [Project1].[Id]
LEFT OUTER JOIN (SELECT
[Extent3].[ResponseId] AS [ResponseId],
[Extent3].[Id] AS [Id],
cast(1 as bit) AS [C1]
FROM [dbo].[LogEntries_ResponseLogEntry] AS [Extent3] ) AS [Project2] ON [Extent1].[Id] = [Project2].[Id]
) AS [Project3]
ORDER BY [Project3].[TimeStamp] DESC