実行に4秒かかる次のクエリがあります。
SELECT TX.* FROM TABLE_X TX
INNER JOIN TABLE_Y TY
ON TY.VALUE_ID = VALUE_ID_IN
AND TY.PROD_ID = TX.PROD_ID
WHERE (TX.PLACE_ID1 = VAR_PLACE_ID OR TX.PLACE_ID2 = PLACE_ID)
AND (TX.DATE > TY.FIRST_DATE)
AND (TX.TYPE_ID != VAR_TYPE_ID1_IN AND TX.TYPE_ID != VAR_TYPE_ID2_IN)
AND (TX.COL1 != COL1_IN OR TX.COL2 != COL2_IN)
しかし、それをTEMPORARY TABLE
に保存したい。次のクエリを実行すると、50秒かかります。
INSERT INTO SESSION.TEMP_TABLE_X /*new line to store result*/
SELECT TX.* FROM TABLE_X TX
INNER JOIN TABLE_Y TY
ON TY.VALUE_ID = VALUE_ID_IN
AND TY.PROD_ID = TX.PROD_ID
WHERE (TX.PLACE_ID1 = VAR_PLACE_ID OR TX.PLACE_ID2 = PLACE_ID)
AND (TX.DATE > TY.FIRST_DATE)
AND (TX.TYPE_ID != VAR_TYPE_ID1_IN AND TX.TYPE_ID != VAR_TYPE_ID2_IN)
AND (TX.COL1 != COL1_IN OR TX.COL2 != COL2_IN)
TABLE_X = 300 000行
TABLE_Y = 90 000行
どうすれば50秒の実行時間を短縮できますか?
サーバーはDB2 v9.5を実行しています。
コメントしやすいので、これを答えとして取り上げます。
一般に、すべてのテーブルでRUNSTATSを実行する必要があります(少なくとも週に1回は投票します)。これにより、オプティマイザにレコードの数(および指定されている場合は、私がお勧めします)のレコード間のデータの分布がわかります。この情報を使用して、オプティマイザはアクセスパスに関してより適切な決定を行うことができます。
オプティマイザもパッケージを使用します。パッケージをREBINDINGすると、基本的に、見つかったRUNSTATSに基づいてパッケージ(つまり、それらのアクセスパス)が変更されます。
あなたの場合、気になるテーブルでRUNSTATSを実行できます
RUNSTATS ON TABLE <schema>.<table> WITH DISTRIBUTION AND DETAILED INDEXES ALL
テーブルがたくさんある場合は、動的にハンティングすることをお勧めします
--do note syntax is for Unix, having to worry about escape characters and what not.
db2 -tnx "select 'runstats on table ' ||
ltrim(rtrim(tabschema))||'.'||ltrim(rtrim(tabname))
|| ' with distribution and detailed indexes all ;'
from syscat.tables where type = 'T' and ownertype = 'U' and
tabschema not in ('SYSCAT','SYSIBM','SYSIBMADM','SYSPUBLIC','SYSSTAT','SYSTOOLS')
order by tabschema asc" >> runstats.sql
これをデータベースに読み込んで実行できます
db2 -tvf runstats.sql
REBIND
s db2rbind
ユーティリティを使用するのが最も簡単です。特定のパッケージ名をすべて知っている必要はありません。私たちは小さなお店なので、毎回次の構文を使用する傾向があります。
db2rbind <my db> -l rebind.log all -r any
エラーがある場合は、ログに表示されます。
したがって、通常は最初にRUNSTATS
を発行し、次にCOMMIT
を発行してロックを解放する必要があります。次に、REBIND
s〜db2rbind
を実行できます。しばらくこれらを実行していない場合は、RUNSTATS
とdb2 flush package cache dynamic
の間にdb2rbind
を入れることをお勧めします。
一時テーブルには常にこの問題があります。 CPUリソースを大量に消費します。説明を行うと、アクセスタイプ「R」またはテーブルスキャンが表示されます。私はそうは思いません、あなたはそれをもっと良くすることができるでしょう。幸運を!