このような質問があります。SELECT によって返されるデータの量 (つまり、文字数) が境界を超えるまで、私が期待するインデックスを使用する実行計画があります。その時点で、プランはインデックスを使用しなくなり、クエリは 100 倍以上遅くなります。
を使えばNVARCHAR(203)
速いです。NVARCHAR(204)
遅い。また、インデックスを使用しない場合は、CPU を完全に消費します。少なくともデータサイズの問題のように思えますが、洞察を探しています。
oldValueString と newValueString を NVARCHAR(255) に変更したところ、状況は少し良くなりましたが、プラン内のインデックスを失うことなくすべての列を照会することはまだできません。
SELECT
[Lx_AuditColumn].[auditColumnPK],
CONVERT(NVARCHAR(204), [Lx_AuditColumn].[newValueString])
FROM
[dbo].[Lx_AuditColumn] [Lx_AuditColumn],
[dbo].[Lx_AuditTable] [Lx_AuditTable]
WHERE
[Lx_AuditColumn].[auditTableFK] = [Lx_AuditTable].[auditTablePK]
AND
[Lx_AuditTable].[createdDate] >= @P1
AND
[Lx_AuditTable].[createdDate] <= @P2
ORDER BY
[Lx_AuditColumn].[auditColumnPK] DESC
これがテーブルの基本構造です (いくつかのインデックスと FK 制約を削除しました)。
CREATE TABLE [dbo].[Lx_AuditTable]
(
[auditTablePK] [int] NOT NULL IDENTITY(1, 1) ,
[firmFK] [int] NOT NULL ,
[auditMasterFK] [int] NOT NULL ,
[codeSQLTableFK] [int] NOT NULL ,
[objectFK] [int] NOT NULL ,
[projectEntityID] [int] NULL ,
[createdByFK] [int] NOT NULL ,
[createdDate] [datetime] NOT NULL ,
CONSTRAINT [Lx_PK_AuditTable_auditTablePK] PRIMARY KEY CLUSTERED
(
[auditTablePK]
) WITH FILLFACTOR = 90
)
GO
CREATE INDEX [Lx_IX_AuditTable_createdDatefirmFK]
ON [dbo].[Lx_AuditTable]([createdDate], [firmFK])
INCLUDE ([auditTablePK], [auditMasterFK])
WITH (FILLFACTOR = 90, ONLINE = OFF)
GO
CREATE TABLE [dbo].[Lx_AuditColumn]
(
[auditColumnPK] [int] NOT NULL IDENTITY(1, 1) ,
[firmFK] [int] NOT NULL ,
[auditTableFK] [int] NOT NULL ,
[accessorName] [nvarchar] (100) NOT NULL ,
[dataType] [nvarchar] (20) NOT NULL ,
[oldValueNumber] [int] NULL ,
[oldValueString] [nvarchar] (4000) NULL ,
[newValueNumber] [int] NULL ,
[newValueString] [nvarchar] (4000) NULL ,
[newValueText] [ntext] NULL ,
CONSTRAINT [Lx_PK_AuditColumn_auditColumnPK] PRIMARY KEY CLUSTERED
(
[auditColumnPK]
) WITH FILLFACTOR = 90 ,
CONSTRAINT [Lx_FK_AuditColumn_auditTableFK] FOREIGN KEY
(
[auditTableFK]
) REFERENCES [dbo].[Lx_AuditTable] (
[auditTablePK]
)
)
GO
CREATE INDEX [Lx_IX_AuditColumn_auditTableFK]
ON [dbo].[Lx_AuditColumn]([auditTableFK])
WITH (FILLFACTOR = 90, ONLINE = OFF)
GO
良い:
悪い: