0

再構築しているクエリから次のスニペットがあります。

LEFT JOIN (SELECT ACCOUNT_ID, LETTER_TYPE, LETTER_DATE, LETTER_ID
           FROM (SELECT T1.ACCOUNT_ID, T2.LETTER_TYPE, T1.LETTER_DATE, T1.LETTER_ID,
                 DENSE_RANK() OVER (PARTITION BY T1.ACCOUNT_ID, T2.LETTER_TYPE
                                    ORDER BY T1.LETTER_DATE DESC) AS RANK1
                 FROM tableOne T1
                 INNER JOIN tableTwo T2 ON T1.LETTER_ID = T2.LETTERID)
           WHERE RANK1 = 1)

私は実際にこれまで扱ったことはありませんDENSE_RANK()PARTITION BY、私の調査に基づくと、このケースは「このレコードのグループをACCOUND_IDとLETTER_DATEの降順で並べ替える」と解釈され、外側のSELECTはRANK=1のレコードのみを取得します。各アカウントに送信された最新のLETTER_IDを検索します。

私の質問は:A。それは正確な翻訳ですか?およびB.このクエリをこのようにネストする必要がないように、このクエリを書き換え/再構築する方法はありますか?

Bで意味するのは、最初にすべてのLETTER_IDを返し、次ににフィルタリングされるということWHERE RANK1 = 1です。それらのすべてのレコードをすぐに破棄するためだけに返すのは、いくぶん無駄のように思えます

4

1 に答える 1

2

クエリを次のように書き直すことができます。

LEFT JOIN (select t1.account_id, t2.letter_type, MAX(t1.letter_date) as MaxDate
           from tableOne t1 join tableTwo t2 on T1.LETTER_ID = T2.LETTERID
          ) maxt left outer join
          (select T1.ACCOUNT_ID, T2.LETTER_TYPE, T1.LETTER_DATE, T1.LETTER_ID
           from tableOne t1 join tableTwo t2 on T1.LETTER_ID = T2.LETTERID
          ) t
          on t.account_id = tmax.account_id and t.letter_type = tmax.letter_type and
             t.letter_date = tmax.maxdate

ただし、ウィンドウ/分析関数はSQLに非常に強力に追加されているため、それらの使用方法を学ぶ必要があります。

ただし、この場合の1つの質問。最新のletter_dateに複数の文字がある場合、クエリ(およびこれも)はすべての文字を返します。おそらくあなたの意図はそれらのうちの1つだけを返すことです。その場合は、row_number()の代わりに使用できますdense_rank()

于 2013-01-07T15:43:36.143 に答える