2012-04-18 11 views
0

背景

現在、私はDB2 V9バージョンを使用しています。私のストアドプロシージャの1つが実行に時間がかかります。私はBMC apptuneを見て、次のSQLを見つけました。 次のクエリを実行するために使用したテーブルが3つあります。
ACCOUNTテーブルは EXCHANGE_RATEは1267K、レコード バランスがDB2 V9 ZOSパフォーマンスチューニング

誰かがクエリのコードの最近以下の部分を追加した113Mレコードを持っている持っている3413件のレコードを持っています。私はこれのために問題があったと思います。

AND (((A.ACT <> A.EW_ACT)    
     AND (A.EW_ACT <> ' ')      
     AND (C.ACT = A.EW_ACT))   
    OR (C.ACT = A.ACT))     

クエリ

SELECT F1.CLO_LED        
INTO :H :H 
FROM (SELECT A.ACT, A.BNK, A.ACT_TYPE,         
      CASE WHEN :H = A.CUY_TYPE THEN DEC(C.CLO_LED, 21, 2)     
      ELSE DEC(MULTIPLY_ALT(C.CLO_LED, COALESCE(B.EXC_RATE, 0)), 21, 2)   
      END AS CLO_LED       
     FROM ACCOUNT A        
     LEFT OUTER JOIN EXCHANGE_RATE B     
     ON B.EFF_DATE = CURRENT DATE - 1 DAY   
     AND B.CURCY_FROM = A.CURNCY_TYPE  
     AND B.CURCY_TO = :H   
     AND B.STA_TYPE = 'A'     
     , BALANCE C       
     WHERE A.CUSR_ID = :DCL.CUST-ID 
     AND A.ACT = :DCL.ACT 
     AND A.EIG_RTN = :WS-BNK-ID     
     AND A.ACT_TYPE = :DCL.ACT-TYPE  
     AND A.ACT_CAT = :DCL.ACT-CAT 
     AND A.STA_TYPE = 'A'      
     AND (((A.ACT <> A.EW_ACT)    
      AND (A.EW_ACT <> ' ')      
      AND (C.ACT = A.EW_ACT))   
      OR (C.ACT = A.ACT))     
     AND C.BNK = :WS-BNK-ID     
     AND C.ACT_TYPE = :DCL.ACT-TYPE 
     AND C.BUS_DATE = :WS-DATE-FROM) F1            
WITH UR 

答えて

2

このクエリで起こっている奇妙なものの数があります。そのうちの最も魅力的なものは、明示的な結合を暗黙的な結合構文と混合することです。率直に言って、システムがそれをどのように解釈するかはわかりません。また、入力と出力の両方に同じホスト変数を使用しているように見えます。しないでください。
また、列名が非常に短い理由は何ですか? DB2(少なくともそのバージョン)は、はるかに長い列名をサポートしています。可能であれば、人々の正気を救ってください。

私たちは物事が遅い理由を完全には伝えられません - アクセスプランを見る必要があるかもしれません。

SELECT CASE WHEN :inputType = a.cuy_type THEN DEC(b.clo_led, 21, 2) 
      ELSE DEC(MULTIPLY_ALT(b.clo_led, COALESCE(c.exc_rate, 0)), 21, 2) END 
INTO :amount :amountIndicator -- if you get results, do you need the indiciator? 
FROM Account as a 
JOIN Balance as b -- This is assumed to not be a 'left', given coalesce not used 
ON b.bnk = a.eig_rtn 
AND b.act_type = a.act_type 
AND b.bus_date = :ws-date-from 
AND ((a.act <> a.ew_act  -- something feels wrong here, but 
     AND a.ew_act <> ' ' -- without knowing the data, I don't 
     AND c.act = a.ew_act) -- want to muck with it. 
    OR c.act = a.act) 
LEFT JOIN Exchange_Rate as c 
ON c.eff_date = current_date - 1 day 
AND c.curcy_from = a.curncy_type 
AND c.sta_type = a.sta_type 
AND c.curcy_to = :destinationCurrency 
WHERE a.cusr_id = :dcl.cust-id 
AND a.act = :dcl.act 
AND a.eig_rtn = :ws-bnk-id 
AND a.act_type = :dcl.act-type 
AND a.act_cat = :dcl.act-cat 
AND a.sta_type = 'A' 
WITH UR 
FECTCH FIRST 1 ROW ONLY 

他のいくつかの注意事項::一方で、ここで速く形であるかもしれないものに再構築し、クエリ、だ

  1. のみ正確必要な列を指定 - 特定の状況下では、これにより、索引専用アクセスが可能になります。そうしないと、フォローアップ・テーブルへのアクセスが必要になることがあります。しかし、これはおそらくここでは役に立たないでしょう。
  2. COALESCE(c.exc_rate, 0)は何とかオフに感じている - 何の為替レートが存在しない場合は、あなたがそうでなければ有効量可能性があり0の量を返します。いくつかの種類のインジケータを返すか、通常の結合にする必要があります。外部のものではありません。

はまた、このバージョン、およびホスト変数は、テーブル間の条件に加えてを指定している可能性がバージョンの両方を試してみてください。オプティマイザは値を自動的に通勤できる必要がありますが、一部の条件(実装の詳細)では不可能です。

関連する問題