[英]SQL Server ROW_NUMBER() Issue
我正在使用row_number()表達式,但沒有得到預期的結果。 我有一個sql表,有些行是重復的。 它們具有相同的“ BATCHID”,我想為它們獲取第二行號,對於其他人,我使用第一行號。 我該怎么做?
SELECT * FROM (SELECT * , ROW_NUMBER() OVER (PARTITION BY BATCHID ORDER BY SCAQTY) Rn FROM SAYIMDCPC ) t
WHERE Rn=1
這段代碼僅向我返回第一行,但我想為重復項獲得第二行。
ROW_NUMBER()
為每一行賦予唯一的計數器。 您想使用RANK()
,這很相似,但是給具有相同值的行賦予相同的分數:
SELECT *
FROM (SELECT * , RANK() OVER (PARTITION BY batchid ORDER BY scaqry) rk
FROM sayimdcpc) t
WHERE rk = 1
如果某些值僅顯示一次,而某些值顯示兩次(也許兩次以上),則您不希望“第一”行,而想要“ max”行。 嘗試逆轉您的訂單條件:
SELECT *
FROM (SELECT * ,
ROW_NUMBER() OVER (PARTITION BY BATCHID ORDER BY SCAQTY DESC) Rn
FROM SAYIMDCPC ) t
WHERE Rn=1
附帶說明一下,最好將所有列都明確列出。 例如,您可能不需要此查詢之外的Rn
...
只需嘗試一下,
SELECT * FROM (SELECT * , ROW_NUMBER() OVER (ORDER BY SCAQTY) Rn FROM SAYIMDCPC ) t
WHERE Rn=1
請嘗試這個。 它將選擇最大行數,如果沒有重復,則應為第一個,否則為第二個
select * from (SELECT * , ROW_NUMBER() OVER (PARTITION BY BATCHID ORDER BY SCAQTY) Rn FROM SAYIMDCPC ) d,
(SELECT batchid,max(Rn) maxRn FROM (SELECT * , ROW_NUMBER() OVER (PARTITION BY BATCHID ORDER BY SCAQTY) Rn FROM SAYIMDCPC ) t
group by batchid) q
where d.batchid = q.batchid and d.rn = q.maxrn
換句話說,這聽起來像是在說:“當批次ID有一行時,請返回該行。如果有2行或更多行,請返回第二行。” 這將需要檢查您的Rn
值以查看其最大值。 我認為您無法在單個查詢中做到這一點。
所以我會嘗試這樣的事情:
WITH NumberedRows AS (
SELECT * ,
ROW_NUMBER() OVER (PARTITION BY BATCHID ORDER BY SCAQTY) Rn
FROM SAYIMDCPC
)
, MaxNumber AS (
SELECT Max(RN) as MaxRn,
BATCHID
FROM NumberedRows
GROUP BY BATCHID
)
, NonDupes AS (
SELECT *
FROM NumberedRows
WHERE BATCHID NOT IN (SELECT BATCHID FROM MaxNumber WHERE MaxNumber = 1)
)
, SecondRows AS (
SELECT (
FROM NumberedRows
WHERE BATCHID NOT IN (SELECT BATCHID FROM MaxNumber WHERE MaxNumber > 1)
AND Rn = 2
)
SELECT
FROM NonDupes
UNION ALL
SELECT *
FROM SecondRows
包含重復項和不重復項的總結果集。 第一列“ IsDuplicate”指示該列是否重復。
;WITH d1 AS (
SELECT Seq = ROW_NUMBER() OVER (PARTITION BY BATCHID ORDER BY SCAQTY)
,*
FROM SAYIMDCPC
)
SELECT IsDuplicate = CONVERT(BIT, Seq)
,*
FROM d1
這只會給您重復項:
;WITH d1 AS (
SELECT Seq = ROW_NUMBER() OVER (PARTITION BY BATCHID ORDER BY SCAQTY)
,*
FROM SAYIMDCPC
)
SELECT IsDuplicate = CONVERT(BIT, Seq)
,*
FROM d1
WHERE Seq > 1
這只會給您非重復項(如您的第一個查詢)
;WITH d1 AS (
SELECT Seq = ROW_NUMBER() OVER (PARTITION BY BATCHID ORDER BY SCAQTY)
,*
FROM SAYIMDCPC
)
SELECT IsDuplicate = CONVERT(BIT, Seq)
,*
FROM d1
WHERE Seq = 1
如果我錯了請糾正我
e.g sample data
BatchID, SCAQTY
1 , 10
2 , 10
2 , 20
2 , 30
您的期望結果如下嗎?
**Expectation Result 1**
BatchID , SCAQty
1 , 10
2 , 30
要么
**Expectation Result 2**
BatchID , SCAQty
1 , 10
2 , 20
2 , 30
根據我的理解,您想要執行的是期望結果1,所以我想下面的查詢應該可以幫助您,您只需要在查詢中添加SCAQTY的desc
SELECT * FROM (SELECT * ,
ROW_NUMBER() OVER (PARTITION BY BATCHID ORDER BY SCAQTY DESC) Rn FROM SAYIMDCPC ) t
WHERE Rn=1
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.