Sql-Server

僅返回符合某些條件的 1 行

  • April 30, 2020

這是我經常遇到的一個問題,我很想知道如何解決這個問題。

我正在編寫一個足夠簡單的報告/查詢,但是在執行時,會返回具有重複值的行。我知道返回這些“重複項”的原因是因為有一列在兩行之間具有不同的數據,但是說我只想看到返回具有特定 ID 號的 1 行。選擇哪一行並不重要,只是每個 ID_NUM 只返回 1 行。

返回數據的簡化範例:

ID_NUM  |  PHASE  |  DATE  |  NOTE  
----------------------------------
30329   |  Phase1  | 1-1-20 | example note
30329   |  null    | 1-1-20 | example note
21928   |  Phase1  | 1-2-20 | another note
21928   |  Phase1  | 4-3-19 | another note

我試過的:

  • SELECT DISTINCT - 返回與簡單 SELECT 相同的結果
  • SELECT DISTINCT MIN(ID_NUM) - 仍然返回重複的 ID_NUM 值,我猜是因為它們是相同的,沒有最小值。
  • GROUP BY ID_NUM - 要求我在 group by 中包含每一列,並且仍然返回相同的結果。

實際範例:雖然上面是一個簡化範例,但下面顯示了我的實際查詢。case.casenum 是我只需要為每個唯一值返回 1 行的欄位/列。這是一個sybase 數據庫,它遵循mssql/t-sql 語法。

SELECT cases.casenum,
cases.case_date_5, 
cases.class, 
user_tab6_data.trial_phase, 
user_tab6_data.maximizer_completed, 
user_tab6_data.maximizer_scheduled, 
cases.case_title, 
cases.open_status, cases.case_date_9, 
user_tab6_data.maximizer_necessary, 
cases.staff_1, 
cases.staff_8, 
user_tab6_data.county_of_suit, 
insurance.how_settled, 
insurance.policy_type, 
insurance.date_settled, 
user_tab6_data.value_set_date, 
user_tab6_data.status_note, 
user_tab6_data.minimum_value 
FROM cases, user_tab6_data, insurance 
WHERE (cases.casenum = user_tab6_data.case_id) 
AND (cases.casenum = insurance.case_num) 
AND (cases.class like 'A' OR cases.class like 'B' OR cases.class like 'C' OR cases.class like 'D' OR cases.class like 'E' OR cases.class like 'F' OR cases.class like 'G' OR cases.class like 'H' OR cases.class like 'I' OR user_tab6_data.trial_phase like 'Phase 1' OR cases.case_date_5 is not NULL ) 
AND insurance.policy_type = 'Liability' 
AND cases.open_status = 'O' 
AND cases.case_date_9 is not NULL 

嘗試使用ROW_NUMBER視窗函式,如下例所示:

--demo setup
drop table if exists Table1
go
CREATE TABLE Table1 (
 ID_NUM INTEGER,
 PHASE VARCHAR(6),
 DATE DATE,
 NOTE VARCHAR(12)
);

--solution
INSERT INTO Table1
 (ID_NUM, PHASE, DATE, NOTE)
VALUES
 ('30329', 'Phase1', '1-1-20', 'example note'),
 ('30329', 'null', '1-1-20', 'example note'),
 ('21928', 'Phase1', '1-2-20', 'another note'),
 ('21928', 'Phase1', '4-3-19', 'another note');

select * from
(
select *,ROW_NUMBER() over(partition by ID_NUM order by ID_NUM) as rn from Table1
) a
where rn = 1

| ID_NUM | PHASE  | DATE       | NOTE         | rn |
|--------|--------|------------|--------------|----|
| 21928  | Phase1 | 2020-01-02 | another note | 1  |
| 30329  | Phase1 | 2020-01-01 | example note | 1  |

引用自:https://dba.stackexchange.com/questions/266098