There is a table Remark
that contains data as shown below:
SerialNo | RemarkNo | Desp
=============================================
10 | 1 | rainy
10 | 2 | sunny
11 | 1 | sunny
11 | 2 | rainy
11 | 3 | cloudy
11 | 4 | sunny
12 | 1 | rainy
What query will return the following result:
10 | 1 | rainy
11 | 3 | cloudy
12 | null | null
That is, the second last record in each group should be returned?
Assuming all the RemarkNo for a SerialNo are continuous. The larger the remark number, the later the remark was made. Hence, the second last RemarkNo for SerialNo 10 is 1 with Desp 'rainy'.
Try:
select s.SerialNo, r.RemarkNo, r.Desp
from (select SerialNo, max(RemarkNo) maxRemark from Remark group by SerialNo) s
left join Remark r on s.SerialNo = r.SerialNo and s.maxRemark-1 = r.RemarkNo
Here is some sql pseudo-code to get you started:
select
penultimate.*
from data as penultimate
left join (
/* query on data to return last row frome each group */
) as ultimate
on /* sql to join 2nd last record on each group to last group */
where not ultimate.SerialNo is null
Completely ineffective solution, but works ...
SELECT
SerialNo,
RemarkNo,
(SELECT Desp
FROM Remarks
WHERE SerialNo = r3.SerialNo AND RemarkNo = r3.RemarkNo) Desp
FROM (
SELECT
r.SerialNo,
(SELECT r2.RemarkNo
FROM Remarks r2
WHERE r.SerialNo = r2.SerialNo
ORDER BY r2.RemarkNo DESC
LIMIT 1, 1) RemarkNo
FROM (SELECT DISTINCT SerialNo FROM Remarks) r) r3
Working example: http://sqlfiddle.com/#!2/a1f89/22
来源:https://stackoverflow.com/questions/15453231/select-the-second-last-record-in-each-group