2017-03-05 9 views
1

私は2つのテーブルSQL Serverの実行計画の問題

CREATE TABLE [dbo].[T2] (
    [Id] INT   IDENTITY (1, 1) NOT NULL, 
    [F1] NVARCHAR (100) NULL, 
    [F2] NVARCHAR (100) NULL, 
    [F3] NVARCHAR (MAX) NULL, 
    PRIMARY KEY CLUSTERED ([Id] ASC) 
); 

GO 
CREATE NONCLUSTERED INDEX [IX_T2_F1_F2] 
    ON [dbo].[T2]([F1] ASC, [F2] ASC); 

CREATE TABLE [dbo].[T3] (
    [Id] INT   IDENTITY (1, 1) NOT NULL, 
    [F1] NVARCHAR (100) NULL, 
    [F2] NVARCHAR (100) NULL, 
    [F3] NVARCHAR (MAX) NULL, 
    PRIMARY KEY CLUSTERED ([Id] ASC) 
); 

GO 
CREATE NONCLUSTERED INDEX [IX_T3_F1_F2] 
    ON [dbo].[T3]([F1] ASC, [F2] ASC) 
    INCLUDE([F3]); 

そして、これらを持っている私の実行は

enter image description here

を計画している問題は、なぜクエリ#です2の実行計画がIndex Seek (NonClustered)ではないため、クエリオプティマイザがcをスキャンする理由クラスタ化されていないインデックス{F1,F2}ではなく、PKの光沢のあるインデックス?

更新#1:

Query #2 Stats

+0

これらのテーブルにはおそらく0行があるので、問題はありません。そこに100万行を入れ、あなたの統計を更新してください。 –

+0

@ ta.speot.is両方のテーブルに100k行あります – dizar47

+0

実行計画の矢印は非常に狭いです - SQL Serverは何行目を見積もっていますか? –

答えて

2

SELECT [F1],[F2],[F3] FROM [T2] WHERE ...には3つの列が必要で、IX_T2_F1_F2には2つしか含まれていません。

SQL Serverは、必要なすべての列をカバーしていないインデックスをカバーする場合、時には寛容です。クエリを満たすためには、クラスタ化インデックスと組み合わせてカバーインデックスを使用する必要があります。

1つのインデックス(クラスター化インデックス)をスキャンする方が2つのインデックスを使用するよりも安価で、クラスタード・インデックス・スキャンでプランを取得すると推定しています。

Hereについては、SQL Serverではクラスタインデックスと併用してカバーインデックスを使用する予定です。

+0

私は漠然としてBrent Ozarが索引をカバーすることについてのより良い記事を持っていたこと、そしてそれらが時々無視される理由を覚えていますが、私はそれを見つけることができませんでした。 –

1

あなたの統計情報が最新でない可能性があります。クエリヒントを使用して、SQL Serverに(index(your_index_name))などの優先インデックスを使用させることができます。私はあなたのインデックスのパフォーマンスをチェックするためにこのクエリのヒントを試してみることをお勧めします。

関連する問題