編集:
この質問は締め切られましたが、誰かのお役に立てば幸いです。
問題はディスク(クラスター)にあります。
PerfMonを使用して、いくつかのカウンター(ディスクの読み取りと書き込み)を作成でき、読み取りカウンターは100%に固定されています。
PAGEIOLATCH_SH:Database_Name:1(*)
ここにいくつかの投稿があり、この警告はI/Oが高いためであると述べています。 SQL Server Books Onlineでは、SQL待機タイプPAGEIOLATCH_SHを次のように定義しています。
I/O要求にあるバッファのラッチでタスクが待機しているときに発生します。ラッチ要求は共有モードです。
この:
ユーザープロセスは、現在バッファキャッシュにないデータを要求します。その時点で– SQL Serverはバッファーページを割り当てようとします–データがディスクからバッファーキャッシュに移動される間、バッファー上に専用のPAGEIOLATCH_EXが作成されます。同時に、ユーザープロセスの観点から、バッファー上にPAGEIOLATCH_SHが作成されます。
インデックスと統計を作成し、SQL Serverプロファイラを使用して支援しました。
クエリを改善する方法はありますか?たくさんのANDs
の処理を改善するにはどうすればよいですか?
この問題は1週間ほど発生しており、どうすればよいかわからない。
SELECT TOP 30 codCliente
FROM (
SELECT t1.CodCliente
, codcampo
, valor
, t1.chavealeat
FROM tblCliente AS t1 WITH(NOLOCK)
INNER JOIN tblClienteDetalhe AS t2 WITH (NOLOCK)
ON t1.codcliente = t2.codcliente
AND CodCampo IN (-1, 4)
WHERE codStatus IN(0)
AND t1.ChavePeriodo < getdate()
AND t1.CodStatusLigacao = 0
AND EXISTS (
SELECT codcliente
FROM tblclientedetalhe WITH (NOLOCK)
WHERE codcampo = 3
AND valor = '2'
AND codcliente = t1.codcliente
)
AND EXISTS (
SELECT codcliente
FROM tblclientedetalhe WITH (NOLOCK)
WHERE codcampo = 6
AND Convert(DateTime,Valor) BETWEEN '2015-03-01' AND '2015-03-31'
AND DateDiff(day,Valor,GetDate()) > 15
AND codcliente = t1.codcliente
)
AND NOT EXISTS (
SELECT 0
FROM tblPesquisa WITH (NOLOCK)
WHERE tblPesquisa.CodCliente = t1.CodCliente
)
AND EXISTS (
SELECT codcliente
FROM tblclientedetalhe WITH (NOLOCK)
WHERE codcampo = 4
AND valor = '161'
AND codcliente = t1.codcliente
)
) AS Cliente
PIVOT (
MAX(Valor)
FOR codCampo in ([4])
) AS PivotTable
WHERE ([4] = '161')
ORDER BY chavealeat;
編集1:
私がコメントで以下に述べたように、この待機ステータスを持つ他のクエリがあります。私はそれが問題ではないことを確認するために仕事が完了するのを待っています。
これは直接あなたの質問に答えないかもしれませんが、あなたはクエリに複数の潜在的な問題を抱えており、それらはすぐに私に見えます。
_AND Convert(DateTime,Valor) BETWEEN '2015-03-01' AND '2015-03-31'
AND DateDiff(day,Valor,GetDate()) > 15
_
なぜCONVERT(DateTime, Valor)
をしているのですか? Valor
はテーブルのDateTime
タイプではありませんか?そうでなければ、あなたはそれを間違っています。
列(DateDiff(day, Valor, GetDate())
)で関数を実行し、それを値と比較すると、SARG非対応になります。代わりにこれを試してください:
AND Valor > DATEADD(DAY, -15, GETDATE())
BETWEEN (x and y)
は、思ったように機能しない場合があります。次の構成は、希望する正確な日付範囲を明示的に定義するため、使用する方がよいでしょう。
_WHERE Valor >= '2015-03-01T00:00:00' AND Valor < '2015-04-01T00:00:00'
_
WITH (NOLOCK)
は高速なボタンではありません! http://blogs.sqlsentry.com/aaronbertrand/bad-habits-nolock-everywhere/ および http://sqlperformance.com/2015/04/t-sql-queriesを参照してください/ the-read-uncommitted-isolation-level ほとんどの場合それがスターターではない理由に関する優れた詳細については。