CTEメモリ空間はどのように機能しますか? CTEを使用して実行する複雑なSQLステートメントがあり、異常に大きな結果セットを取得した場合、クエリの論理読み取りを増やすことができますか?
32兆回の読み取りを実行しているCTEがあり、それ以外の場合は200Kで実行しています
ここで何が起こっているのかわからない私の刺し傷です。小さな結果セットと十分に単純なクエリプランでは、クエリメモリが盗まれたページ(実際に使用されるクエリメモリ許可のその部分)は許可サイズ以下であるため、tempdbへの流出は発生しません。この場合、論理的な読み取りは予想通りです-クエリスレッドはバッファプール内のユーザーオブジェクトページを参照します。だが。盗まれたクエリのページがクエリメモリの許可サイズに達しても、実行するクエリ作業がまだたくさん残っている場合はどうなりますか付与されたすべてのメモリがクエリに対して盗まれると、残りの「クエリメモリ」の内容がtempdbに流出します。これらは通常のバッファープールLRUQをバイパスし、すぐにtempdbに書き込まれます。クエリが後で作業を完了するために再度それらを必要とする場合は、temdbページをバッファープールに読み取り、これらの中間結果にアクセスするときにクエリスレッドが論理読み取りを発生します。したがって、メモリが盗まれたページ参照のクエリ(論理読み取りでカウントされるとは思わない)と同様の作業が、tempdbの内容の論理読み取りになります。
Sys.dm_exec_query_stats(クエリの読み取りと書き込みの統計用)、sys.dm_exec_query_memory_grants(クエリメモリの許可要求サイズと使用済みクエリメモリ用)、sys.dm_db_session_space_usage(セッションで完了したタスクの累積tempdb)、およびsys.dm_db_task_usage(tempdb進行中のタスクの使用)により、この「盗まれたページが最大になり、tempdb論理読み取りを追加してクエリを終了する」ことが発生しているかどうかが明確になるはずです。