0

非常によく似たクエリが 2 つあります。

exec sp_executesql N'SELECT TOP (1) [t0].[Production]
FROM [dbo].[T_Production] AS [t0]
WHERE [t0].[InputID] = @p0
ORDER BY [t0].[Timestamp] DESC',N'@p0 int',@p0=1161

exec sp_executesql N'SELECT TOP (1) [t0].[Production]
FROM [dbo].[T_Production] AS [t0]
WHERE [t0].[InputID] = @p0
ORDER BY [t0].[Timestamp]',N'@p0 int',@p0=1161

最初の 1 つは 1 秒で実行され、もう 1 つは 31 秒で実行されるのはなぜですか?

面白いことに、2 番目のクエリをストア プロシージャから

SELECT TOP (1) [t0].[Production]
FROM [dbo].[T_Production] AS [t0]
WHERE [t0].[InputID] = 1161
ORDER BY [t0].[Timestamp]

それも1秒で実行されます

しかし驚くべきことに、[Timestamp] の後に空白を追加すると、最後の行がこのようORDER BY [t0].[Timestamp] ',N'@p0 int',@p0=1161に表示され、非常に高速に実行されます。

編集:いくつかの調査の後、私は実際の実行計画を確認し、cos は次のとおりでした: select cost:0 -> top cost 6 -> index scan (NonClustered)[T_Production].[_dta_index_T_Production] cost 94

[Timestamp] に降順で新しいインデックスを追加しました。数分かかりましたが、突然、クエリが最初のクエリと同じ速さで実行されるようになりました。

しかし、ここで私は本当に混乱しています。追加のインデックスの順序は昇順でなければならないことに気付きました。すでに降順で持っているので、別のインデックスを作成すると役に立ちましたか? 混乱したので、作成したばかりのこのインデックスを削除しましたが、このクエリは最初のクエリと同じくらい高速に実行されます。たぶん、インデックスの再構築が役に立ちましたか? この問題は再発します。

しかし、インデックスを追加および削除した後、実際の実行計画は異なります。キー ルックアップ (クラスター化).. コスト: 67%

4

1 に答える 1

3

インデックスには、実行プランに影響を与える可能性のあるキーの列にもASCとDESCがあります。

これは、このような単純なクエリとは大きな違いのように見えますが、インデックス定義と実行プランを見ると、おそらくコストのかかる追加の並べ替え操作が必要です。

インデックスを削除すると、キャッシュ内の実行プランがほぼ確実に無効になります。

パラメータスニッフィングを回避するOPTION (RECOMPILE)には、インラインパラメータ化クエリで使用するか、コードをストアドプロシージャに移動してOPTIMIZE FOR UNKNOWN

于 2013-02-19T17:51:12.510 に答える