簡體   English   中英

子查詢從最新記錄返回多個列?

[英]Subquery to return multiple columns from newest record?

我得到了這樣的表結構:

文獻

ID  | NAME  | DATA
----+-------+--------
1   | Doc1  | Data1
2   | Doc2  | Data2

歷史

HID | DOC_ID    | HDATA1    | HDATA2    | HDATA3
----+-----------+-----------+-----------+---------
1   | 1         | A         | B         | C
2   | 2         | C         | D         | E
3   | 1         | A         | A         | B
4   | 1         | B         | B         | D
5   | 2         | E         | A         | C

我想要得到的輸出是來自HISTORY (最高HID)中最新記錄的NAMEDATAHDATA1HDATA2HDATA3HDATA2HDATA3值與Documents表中的相應ID匹配。

我發現的示例僅從一列返回一個值,但是我需要來自多列的數據。 我不知道如何設置此SQL。

以下示例適用於Oracle,並且可能會略微適應不同的SQL方言:

SELECT * 
  FROM ( SELECT h.*,
                d.*,
                RANK() OVER (PARTITION BY h.DOC_ID ORDER BY h.HID DESC) AS RNK
           FROM History h
           JOIN Document d ON d.ID = h.DOC_ID )
 WHERE RNK = 1

經過以下數據測試:

INSERT INTO Document VALUES ( 1   , 'Doc1'  , 'Data1' );
INSERT INTO Document VALUES ( 2   , 'Doc2'  , 'Data2' );

INSERT INTO History VALUES ( 1   , 1         , 'A'         , 'B'         , 'C' );
INSERT INTO History VALUES ( 2   , 2         , 'C'         , 'D'         , 'E' );
INSERT INTO History VALUES ( 3   , 1         , 'A'         , 'A'         , 'B' );
INSERT INTO History VALUES ( 4   , 1         , 'B'         , 'B'         , 'D' );
INSERT INTO History VALUES ( 5   , 2         , 'E'         , 'A'         , 'C' );

結果:

HID     DOC_ID HDATA1     HDATA2     HDATA3             ID NAME       DATA              RNK
---------- ---------- ---------- ---------- ---------- ---------- ---------- ---------- ----------
         4          1 B          B          D                   1 Doc1       Data1               1 
         5          2 E          A          C                   2 Doc2       Data2               1
select * from Document d
inner join (
            select h1.* from  History h1
            inner join (
                         select max(hid) as hid from History group by doc_id 
                        ) h2
            on h1.hid = h2.hid
           ) t
on t.doc_id = d.doc_id 

以下查詢將返回每個文檔ID的最新記錄

   SELECT 
            ID, Name, DATA, HDATA1, HDATA2, HDATA3 
   FROM Document D CROSS APPLY (SELECT TOP 1 HDATA1, HDATA2, HDATA3 FROM History H WHERE D.ID=H.DOC_ID ORDER BY H.HID DESC) A

通過在這種情況下使用交叉應用,查詢成本將相對較低。它可以在查詢估計的執行計划中顯示最佳結果。

使用排序子句中的窗口函數row_number結合TOP 1 with ties有一種非常優雅的方法來實現此目的。 無需子查詢。

select top 1 with ties *
from document d
join history h
    d.id = h.doc_id
order by row_number() over (
            partition by d.id
            order by h.hid desc
            );

它為每個文檔返回具有最新歷史記錄ID的一條記錄。

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM