簡體   English   中英

SQL按has_many關系的最新元素的列選擇

[英]SQL select by column of newest element of has_many relationship

在我的項目中,我有一個tasks (ID,名稱)表。 我也有一個status_updates (id,task_id,user_id,status,created_at)表。

我想選擇其最新status_update等於某個狀態的任務。

但是,我不知道如何組合以下內容:

  1. 僅對每個任務使用最新的status_update。
  2. 過濾掉狀態不正確的status_updates。
  3. 將其包裝在INNER JOIN中,以便最終結果是任務的集合。

使用GROUP_BY時,​​似乎1.和2.互相抵消了。 一個例子:

SELECT * FROM status_updates GROUP BY task_id ORDER created_at DESC

僅返回每個任務的最新status_update。 但是,這:

SELECT * FROM status_updates WHERE status='1' GROUP BY task_id ORDER created_at DESC

在ORDER之前執行WHERE,從而從狀態正確的對象中返回最新的 ,而不是 狀態正確的對象中返回最新的

我也嘗試使用HAVING,但是由於它僅適用於聚合列,因此我無法弄清楚如何正確使用它,或者在這種情況下它是否完全有用。

我正在使用Ruby on Rails,因此我想在MySQL和SQLite上都可以使用。

使用子查詢:

SELECT
    T.id,
    T.name,
    SU.status
FROM
    Tasks T
INNER JOIN (SELECT task_id, MAX(created_at) AS max_created_at FROM Status_Updates GROUP BY task_id) SQ ON SQ.task_id = T.id
INNER JOIN Status_Updates SU ON
    SU.task_id = SQ.task_id AND
    SU.created_at = SQ.max_created_at
WHERE
    SU.status = '1'

使用窗口函數和CTE(盡管RDBMS當前不支持它們,但將來會有很多)。 這個優點是可以更好地處理聯系:

WITH MyCTE AS
(
    SELECT
        T.id,
        T.name,
        SU.status,
        ROW_NUMBER OVER(PARTITION BY T.id ORDER BY SU.created_at DESC, id DESC) AS row_num
    FROM
        Tasks T
    INNER JOIN Status_Updates SU ON SU.task_id = T.id
)
SELECT
    id,
    name,
    status
FROM
    MyCTE
WHERE
    row_num = 1

暫無
暫無

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

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