[英]How to SELECT rows with MIN(DateTime column), GROUP by another column and DISTINCT by another column in SQL?
我的桌子是:
ID | 學生卡 | 考試日期 | 執照 | 結果 |
---|---|---|---|---|
1 | 101 | 01-11-2020 | B2 | 失敗的 |
2 | 102 | 15-11-2020 | 一個 | 通過 |
3 | 103 | 22-11-2020 | D | 失敗的 |
4 | 101 | 01-10-2020 | D | 通過 |
5 | 104 | 01-12-2020 | 一個 | 通過 |
6 | 103 | 29-11-2020 | D | 通過 |
7 | 101 | 01-12-2020 | B2 | 通過 |
8 | 105 | 01-09-2020 | B2 | 失敗的 |
9 | 104 | 01-11-2020 | 一個 | 失敗的 |
10 | 105 | 01-11-2020 | B2 | 通過 |
我需要 select 根據每個學生 ID 和許可證列,根據考試日期獲得第一個結果的結果。 如果同一個學生參加不同的執照考試,這兩個結果也需要拿出來。 但是對於每個學生 ID 和許可證值,我只需要一個結果行。
結果應如下所示:
ID | 學生卡 | 考試日期 | 執照 | 結果 |
---|---|---|---|---|
1 | 101 | 01-11-2020 | B2 | 失敗的 |
2 | 102 | 15-11-2020 | 一個 | 通過 |
3 | 103 | 22-11-2020 | D | 失敗的 |
4 | 101 | 01-10-2020 | D | 通過 |
8 | 105 | 01-09-2020 | B2 | 失敗的 |
9 | 104 | 01-11-2020 | 一個 | 失敗的 |
我已經完成了研究和查詢,到目前為止,盡管學生參加了兩次不同的執照考試,但我只得到了 1 行的 student_id。
以下是我的查詢:
SELECT scct_outer.id, scct_outer.stud_id, scct_outer.exam_date, scct_outer.license, scct_outer.result
FROM stud_cdl_comp_test AS scct_outer
INNER JOIN
(SELECT stud_id, MIN(exam_date) AS MinExamDate
FROM stud_cdl_comp_test AS scct
INNER JOIN stud AS s ON scct.stud_id = s.id
INNER JOIN agent_profile AS ap ON s.agent_profile_id = ap.id
GROUP BY stud_id) groupedscct
ON scct_outer.stud_id = groupedscct.stud_id
AND scct_outer.exam_date = groupedscct.MinExamDate
在這種情況下,認為您在這種情況下按 student_id 分組幾乎是不正確的。 實際上分組的是學生+許可證。 我們稱這個組合鍵為individual_license
。
解決方案如下所示:
SELECT
st.id,
st.stud_id,
st.exam_date,
st.license,
st.result
FROM stud_cdl_comp_test AS st
INNER JOIN
(SELECT
MIN(exam_date) AS min_date,
st_inner.student_id,
st_inner.license
FROM stud_cdl_comp_test AS st_inner
GROUP BY st_inner.student_id, st_inner.license
) grouped_inner
ON grouped_inner.student_id = st.student_id
AND grouped_inner.license = st.license
AND grouped_inner.min_date = st.exam_date;
這應該有效。
您的原始代碼的問題是它缺少外部查詢和子查詢之間的許可證相關性。 您可以將其表述為:
select s.*
from stud_cdl_comp_test s
inner join (
select student_id, licence, min(exam_date) as minexamdate
from stud_cdl_comp_test as scct
group by stud_id, licence
) s1 on s1.student_id = s.student_id and s1.license = s.license and s1.minexamdate = s.date
我不知道stud
和agent_profile
是什么,所以我從查詢中刪除了。
也就是說,這不是我推薦的方法 - 一個簡單而有效的選擇是使用子查詢進行過濾:
select *
from stud_cdl_comp_test s
where s.exam_date = (
select min(s1.exam_date)
from stud_cdl_comp_test s1
where s1.student_id = s.student_id and s1.license = s.license
)
這可以利用(student_id, license, exam_date)
上的索引。
或者,您可以使用 MySL 8.0 中提供的row_number()
:
select *
from (
select s.*,
row_number() over(partition by student_id, licence order by exam_date) rn
from stud_cdl_comp_test s
) s
where rn = 1
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.