首頁
編程語言
C語言|JAVA編程
Python編程
網頁編程
ASP編程|PHP編程
JSP編程
數據庫
MYSQL數據庫|SqlServer數據庫
Oracle數據庫|DB2數據庫
您现在的位置: 程式碼之家 >> 編程語言 >  >> 更多程式語言 >> 程式設計綜合問答

SQL Server 分組排序取整行:避開 MAX() 陷阱的正確姿勢

     編輯:程式設計綜合問答

常見誤區:以為 GROUP BY id ORDER BY date DESC 配合 MAX(value1) 就能取得「日期最大那一行的 value1」。實則 MAX() 是逐欄獨立取最大,導致 value1、value2 可能來自不同行,產生錯誤業務結果。

正確核心邏輯:先定「哪一行」,再取「整行資料」

無論資料庫版本,核心步驟只有兩步:

  1. 找出每組的業務主鍵(如 id + max(date) 或自增 row_id)。
  2. 用該主鍵回表/關聯撈取完整列。

通用標準寫法(SQL Server 2005+ 推薦)

WITH Ranked AS (
    SELECT *, ROW_NUMBER() OVER (PARTITION BY id ORDER BY date DESC) AS rn
    FROM Records
)
SELECT id, date, value1, value2
FROM Ranked
WHERE rn = 1;

SQL Server 2000 降級寫法

-- 衍生表 JOIN(最穩健)
SELECT r.id, r.date, r.value1, r.value2
FROM Records r
JOIN (
    SELECT id, MAX(date) AS max_date
    FROM Records
    GROUP BY id
) g ON r.id = g.id AND r.date = g.max_date;

效能關鍵:覆蓋索引

CREATE INDEX IX_Records_Id_Date_Cover ON Records(id, date DESC) INCLUDE (value1, value2);

有了覆蓋索引,無論子查詢、JOIN、CTE,執行計劃皆為 Index Seek + Stream Aggregate,毫秒級返回。

記住:分組排序取整行 = 先算分組鍵 + 最大排序鍵,再 JOIN 回主表,別再被 MAX(column) 逐欄拆解的假象誤導。

  1. 上一篇文章:
  2. 下一篇文章:
Copyright © 程式碼之家 All Rights Reserved